Com vaig crear una web automàtica amb +930 clics en < 3 mesos

Crear una web automatica amb 930 clicks en menys de 3 mesos

Darrera actualització:

No et vendré una web en 5 minuts ni una moto a euro i mig. L’automatització també porta el seu temps i costos, encara que permet accelerar processos i que un únic professional abasti molta més feina. De fet, et mostraré com he creat una web automàtica a WordPressjo solet.

Index de continguts

Petita reflexió sobre el futur laboral i la IA

Des de fa molts anys, l´especialitat professional ha estat un tema de preocupació freqüent per als grans pensadors de la societat. Fins i tot els teòrics sociològics clàssics parlaven del perill que corria l’especialització professional.

Dit de manera ràpida, pensaven que l’especialització provocaria que desconeguéssim el que existia fora del nostre abast professional, i que algunes entitats com la burocràcia acabarien obtenint vida pròpia i estant fora del nostre control. Aleshores, els professionals serien part d’un organisme que no comprendrien íntegrament.

Podem dir que, avui, el paradigma ha canviat. La IA està evolucionant d’una manera inabastable, fins i tot ha arribat a sorprendre Google i altres grans empreses del món digital. A més, naixen nous perfils professionals que abasten un coneixement més horitzontal.

Últimament es parla molt del perfil professional tipus T, el qual compta amb una especialitat i un ampli coneixement de tot allò que envolta la seva matèria principal. Un tipus de professional a qui veig un gran futur. De fet, aquest article és perfecte per a aquest tipus de professionals, si segueixes llegint descobriràs per què.

Valors de rendiment d’aquesta web

Tot i que des del meu punt de vista no són el factor determinant per a l’èxit d’un projecte web, començarem amb els valors de rendiment que sé que a molts us agraden les gràfiques boniques i els números rodons.

Tots els valors que mostro a continuació són del dia en què escric aquest article (12/07/23) o del dia anterior.

Pagespeed Insights

Els valors que trobem en aquesta plataforma no estan gens malament, 99 per a la versió mòbil i 100 per a la versió escriptori. La veritat és que em podria haver posat a optimitzar encara més la càrrega d’arxius, però he dit “per a què”, així podeu veure el que es pot aconseguir amb un servidor d’alt rendiment com Wetopii un tema que carrega ràpid.

Cal tenir en compte que s’han obtingut aquests valors fins i tot usant eines que afecten de forma considerable el rendiment, com ara Clarity de Microsoft, Google Analytics i Complianz.

Rendiment 100 a PageSpeed Insights per a ordinador
Resultats Page Speed Insights de la gairebé totalitat de pàgines.
Resultat de 100 a PageSpeed Insights per a mòbil
Resultat Page Speed de Google, d’una de les pàgines amb més impressions.

Aquests valors són els que llança la pàgina amb més impressions i visites de la web. La resta de pàgines no tenen un valor inferior, n’hi ha diverses que fins i tot tenen 100/100.

Google Search Console

La veritat és que aquesta gràfica és ben bonica, des del dia que es va llançar la web no ha parat de créixer progressivament.

Segons crec, encara li queda temps per enganxar l’estirada, ja que el 50% de les impressions i clics se les estan emportant tan sols 2 pàgines, algunes de les 250 pàgines inicials s’estan començant a posicionar a 1a pàgina ara. Encara queda molt de recorregut.

evolució de les impressions, clics i posició mitjana a Google Search Console
Resultats sobre impressions, CTR i posició, mostrats a Google Search Console

No he afegit el CTR mitjà perquè sigui més visual, però els que esteu acostumats a veure aquestes gràfiques suposo que us en fareu una idea.

Microsoft Clarity

A Clarity he tret una informació força bona per estudiar la interacció dels usuaris. Però com us vull mostrar la molla, us ensenyo una captura del temps que solen passar els usuaris en aquesta web.

Estadístiques de Clarity sobre el temps que passen els usuaris
Resultats audiència des de Microsoft Clarity.

Web automàtica a WordPress i sense plugins

L’ús de WordPress té un gran nombre d’avantatges. Però en aquest cas hauríem de destacar la gran capacitat de personalització a què podem accedir.

Ficaré les mans a la massa i intentar explicar de la millor manera possible com he creat aquesta web

Tecnologies usades per a aquest projecte

  • Eines professionals de màrqueting de continguts per a estudi de Kws i competència
  • ChatGPT API
  • Google Sheets API
  • Leonardo.ai API
  • WordPress, Gutenberg
  • Codi nadiu de WordPress i PHP
  • REST API de WordPress
  • JavaScript (jQuery i jsPDF)
  • MySQL
  • HTML i CSS
  • Keyword combinator
  • Shuffle text lines
  • NES
  • Bash
  • Python

Passos en crear aquesta web automatitzada a WordPress

He volgut dedicar el meu temps a la planificació del projecte. Els passos han estat els següents:

  1. Estudi de Kws i competència
  2. Planificació de passos a seguir
  3. Preparació de fitxer a Google Sheets
  4. Assaig de prompts amb l’API de xatGPT
  5. Públic objectiu
  6. Disseny de la web
  7. Creació d’un tema a WordPress per a l’ocasió
  8. Crear el contingut principal de la web a WordPress amb les API de chatGPT4, de Google Sheets i de Leonardo.ai
  9. Crear la resta del contingut
  10. Registre i membres
  11. Últims retocs
  12. Aplicació per crear articles automàtics programats mitjançant un NAS i Python

Sobre el projecte

Aquest web automatitzat tracta sobre una temàtica que vaig considerar molt apropiadaper treballar amb chatGPT per diversos motius:

  • No hi haurà errors informatius provinents de la IA
  • El contingut automàtic és 99% creatiu
  • A través d´una sèrie d´implementacions farem que els usuaris fàcilment interaccionin amb la web
  • La intenció de cerca dels usuaris és molt clara
  • Podrem oferir un “Link Magnet” senzill i que probablement funcioni bé
  • El nínxol no està explotat per webs verticals
  • Es poden crear 250 URLs (fins i tot més) sense por de trobar errors

Tot i que jo sóc més de Lovecraft, aquest projecte és molt Danielle Steel. Sí, ja ho sé, és una mica cursi, però escolta, si funciona funciona…

Per motius evidents no facilitaré el domini de la web en qüestió, però si voleu anar coneixent més detalls d’aquest projecte aniré publicant a LinkedIn com va creixent. I quan cregui que està establert a la seva temàtica ho faré públic.

A més, encara vull implementar diversos mètodes de monetització i no vull que a qualsevol que vegi la web se li encengui la bombeta.

El que sí que puc dir d’aquesta web automàtica és que:

  1. Ofereix un contingut creatiu força cercat a Google
  2. Aquest contingut es mostra a la web com a exemple
  3. Es dóna la capacitat deditar el contingut creatiu
  4. Hi ha una caixa perquè els usuaris puguin crear contingut creatiu nou mitjançant IA
  5. Hi ha un botó per enviar el contingut generat per WhatsApp
  6. Si els visitants es registren es dóna la capacitat de descarregar en PDF el contingut d’exemple, creat i/o editat

Com podem veure, la interacció de lusuari és vital en aquest projecte. I crec que gràcies a això s’estan creant uns temps a les pàgines força bons. Per exemple, una pàgina té al juny un temps d’interacció mitjà de 10’25”i hi ha algunes visites que superen els 40 minuts!

Estudi de Kws i competència

He utilitzat diverses eines professionals per a lestudi de paraules clau. La veritat és que no recordo com vaig arribar a trobar la kw arrel de la qual va néixer tot el projecte. Suposo que estaria investigant algun competidor d’algun altre projecte.

Però quan vaig trobar em va sorprendre el fet que no existís cap web que li donés resposta de manera vertical. Així que em vaig descarregar un fitxer CSV amb totes les paraules clau que aquesta eina em va facilitar per treballar una estructura dURL interessant.

Planificació

Amb el fitxer CSV vaig poder escollir les Kws més interessants ia les que els veia una mica de futur. Així que les vaig resumir en 2 grups, 1 categoria principal i una categoria secundària. És a dir, tots aquests articles pertanyen a dues categories.

Categoria principal

  • nuvi
  • núvia
  • mare
  • pare
  • germana
  • germà
  • amic
  • amiga
  • marit
  • dona
  • fill
  • filla

Categoria secundària

  • per plorar
  • originals
  • amb sentiment
  • llargues
  • curtes
  • per a aniversari
  • per a sant valentin
  • per a comiats
  • ultimes
  • boniques
  • inoblidables
  • romantiques
  • per a la distància
  • per a aniversari
  • no cursis
  • virtuals
  • tristos
  • sinceres
  • per demanar perdó
  • amb dolor
  • formals
  • poètiques
  • per trobar a faltar
  • per als bons dies
  • de reconciliació

Preparació de fitxer a Google Sheets

La preparació del nostre Google Sheets és molt important en aquest projecte, ja que contindrà l’estructura de tota la web, així com els prompts més importants del contingut automatitzat.

Vaig dividir el fitxer en 10 columnes per alimentar els prompts:

  1. Rol
  2. Kw
  3. Kws secundàries
  4. Categoria principal
  5. To
  6. URL
  7. Categoria secundària
  8. Quantitat de paraules
  9. Substantius
  10. Prompt

O sigui, sense la columna del Prompt, quedaria una cosa així:

RolKwKws secundàriescap a/cattourlcategoriesparaulesSubstantius
núviaploraremoció, afecte, amor, t’estimonuvimalenconiós i afectuósplorarper fer plorar800coixí, camisa, color
núviat’estimoallà on arribem, en els meus somnis, he perdut el seny, ets com l’arròs xinès i jo els escuradentsnuvioriginal, creatiu, afectuós i divertitoriginaloriginal900abella, carrer, toll
núviael meu corentranyes, passió, alegria, bogerianuvisentimental, passionalsentimentamb sentiment800aigua, bota, clima

Com ja us haureu imaginat, cada línia serà una URL independent.

Escriure 250 línies amb contingut únic seria una feina de setmanes. Així que sempre podrem trobar eines d’automatització per a això.I com ho he fet? Molt senzill, he entrat a chatGPT (versió 3.5) i us he preguntat “Escriviu un complet llistat de tons d’escriptura que chatGPT pot interpretar”.

Els resultats els he dividit en 3 i els he afegit a 3 columnes a Keyword combinator, una eina que permet crear cadenes de text amb el separador que creguem convenient, en aquest cas la coma.

Després he afegit el resultat en una altra eina anomenada Shuffle Text Lines, la qual barrejarà totes les línies per donar-nos un resultat aleatori. I bé, així tindrem tots els valors per a la columna to en menys de 10 minuts.

Per a la columna Kws secundàries he fet el mateix però canviant la pregunta a chatGPT. Aquesta seria: “Escriu-me una llista de 100 paraules que encaixin amb la paraula clau principal d’aquest projecte”.

Per afegir encara més autenticitat a cada article he demanat a chatGPT que generi un xàfec de substantius separats per comes. I igual que per a les altres columnes he fet servir les eines Keyword combinator i Shuffle Text Lines.

I finalment el treball més avorrit, escollir Kw principal per a cada article i revisar una a una cada línia per veure que tot encaixa bé. Aquest treball manual serveix per verificar que tota l’estructura dels prompts té sentit, ja que en col·locar el to i les paraules clau secundàries de forma aleatòria és molt probable que hi hagi incongruències.

He de dir que encara que vaig afegir el camp de quantitat de paraules, chatGPT s’ho va passar pel folre.

Assaig de prompts amb l’API de xatGPT

Abans de començar amb el desenvolupament he dedicat un bon temps exclusivament a veure com l’API de chatGPT responia als promptsper trobar el que s’ajustava més al que volia.

En voler que es publiqués tot a Gutenberg de forma automàtica, no he trobat manera que chatGPT generi el contingut amb les etiquetes HTML i els comentaris característics de Gutenberg.

També, un altre problema que vaig trobar és que sempre tornava el contingut HTML amb les etiquetes <body> i <head>.

Aquests problemes els he hagut de solucionar en el processament posterior mitjançant PHP.

Creació d’un tema a WordPress per a l’ocasió

A més que els servidors de Wetopiem van sorprendre quant a velocitat, he volgut anar un pas més enllà i he creat un tema personalitzat per a aquest projecte.

M’he limitat a afegir els fitxers imprescindibles, a més d’un parell de page-templates, una carpeta amb els fitxers .js i una altra amb els fitxers .css.

Els page-templates els fan servir per crear l’estructura concreta de cada grup de pàgines/posts i per posar en cua els fitxers .js i .css concrets de cadascun. Això últim ho faig mitjançant la funció condicional is_page_template(). D’aquesta manera podem segmentar i treure el CSS que no es faci servirde cada pàgina concreta del nostre WordPress.

Públic objectiu

No sóc un expert en màrqueting, i definir el públic objectiu és una tasca que sempre m’ha costat força.

Tot i que en aquest projecte tenia una idea inicial relativament clara quant als usuaris que hi accediran de forma orgànica, em vaig adonar que hi havia algunes cerques que se’n sortien.

Per exemple, per a les categories nuvi amb sentiment, intuïa que les cerques serien més de noies i nois d’entre 14 i 25 anys. Però per a categories com a fill trobar a faltar, suposo que els usuaris i usuàries que fessin aquestes cerques serien mares i pares d’entre 30 i 50 anys.

Una cosa que tenia clar és que aquesta web funcionaria a sud-amèrica fins i tot millor que a Europa. I la veritat, ara com ara sembla que està sent així.

Disseny de la web

M’he decidit a crear una petita membresia on es demana edat i mail per accedir a la possibilitat de descàrrega del PDF amb el contingut d’exemple, creat i/o editat. Així vaig obtenint els mails per a una possible newsletter en el futur.

A més, el disseny que al principi he creat és molt sobri, neutre, diria que fins i tot feut. Quan tingui una quantitat de dades demogràfiques considerable canviaré el disseny de la web. I bé, dir que després de 3 mesos estant en línia, les dades revisades m’han sorprès força:

Rang d'edat dels usuaris de la wev

I jo pensava que els visitants tindrien entre 14 i 25 anys… Encara sort que no vaig crear un disseny enfocat en aquest públic!.

Els detalls gràfics de la web que no han estat generats mitjançant API externa, com ara el logo, les icones de la home, etc. s’han creat a SVG per a una càrrega més ràpida. Per permetre pujar SVG a WordPress cal configurar un parell de cosetes en codi, ja que per defecte no es pot.

Crear el contingut principal de la web a WordPress amb les API de chatGPT, Google Sheets i Leonardo.ai

Em limitaré a explicar “en prosa” com he desenvolupat el plugin per generar el contingut automàtic, perquè com em posi en pla tutorial no donarà temps que ens mengem el raïm. Però si us sorgeix algun dubte estaré encantat de respondre-vos a través de LinkedIn.

Cal tenir en compte que aquest plugin s’ha creat per a ús en local, sota un servidor Apache.

Aquest plugin consta de 3 arxius amb les classes per a cada API, recordem que he fet servir les APIs de Google Sheets, chatGPT i Leonardo.ai. Compte amb la següent estructura:

Estructura de fitxers per a les APIs de Google Sheets, ChatGPT i Leonardo.ai
  1. Sheets: Aquesta classe conté un únic mètode que realitza la connexió a l’API i obté els valors del Google Sheet prèviament configurat
  2. GPT: Aquesta classe conté:
    • Mètode de connexió a l’API
    • Mètode per generar la introducció
    • Mètode per generar el contingut creatiu
    • Mètode per generar la metadescription
  3. LEO: En aquesta classe he afegit diversos mètodes:
    • Crides per a generació d’imatge
    • Mètode de connexió
    • Crida per obtenir URL d’imatge segons l’ID obtingut al mètode anterior
    • Mètode per pujar imatge a WordPress des d’una URL externa. Aquest mètode sí que em sembla molt útil, així que us el deixo per aquí:
public function up_img( $image_url, $new_name ) {
require_once( ABSPATH . 'wp-admin/includes/file.php' );

        ////Descargamos la imagen a una variable que contiene los datos temporales
        $temporal = download_url( $image_url );

        if( is_wp_error( $temporal ) ) {
            return false;
        }

        //Descargamos el archivo a la carpeta uploads
        $file = array(
            'name'     => basename( $new_name . '.jpg' ),
            'type'     => mime_content_type( $temporal ),
            'tmp_name' => $temporal,
            'size'     => filesize( $temporal ),
        );

        $sideload = wp_handle_sideload(

            $file,
            array(
                'test_form'   => false
            )
        );

        if( ! empty( $sideload[ 'error' ] ) ) {
            return false;
        }

        //Añadimos el archivo a la base de datos para que aparezca en la sección media del panel de control

        $attachment_id = wp_insert_attachment(

            array(
                'guid'           => $sideload[ 'url' ],
                'post_mime_type' => $sideload[ 'type' ],
                'post_title'     => basename( $sideload[ 'file' ] ),
                'post_content'   => '',
                'post_status'    => 'inherit',
            ),

            $sideload[ 'file' ]
        );

        if( is_wp_error( $attachment_id ) || ! $attachment_id ) {
            return false;
        }

        //Actualizamos metadatos
        require_once( ABSPATH . 'wp-admin/includes/image.php' );

        wp_update_attachment_metadata(
            $attachment_id,
            wp_generate_attachment_metadata( $attachment_id, $sideload[ 'file' ] )
        );

        return $attachment_id;
    }

Com heu vist a l’estructura, compte també amb dos fitxers a la carpeta control i un fitxer a la carpeta arrel.

El fitxer arrel no conté més que els fitxers de configuració i activació que tot plugin té. Gràcies a aquest fitxer comptarem amb una secció al tauler de control. I aquí és on entra el fitxer de control acgpt_callback.php:

acgpt_calbback.php inclou un formulari amb un simple botonet que es mostrarà a la secció del plugin del tauler de control de WordPress. Aquest botó trucarà a una funció allotjada al fitxer acgpt_form.php. En aquest darrer arxiu és on succeeix la màgia, i fa el següent:

  1. Es truca a l’API de Google Sheets i s’obtenen les files
  2. Es crea un bucle per tractar les files 1 a 1
  3. S’obtenen les dades de categories, rol, cap i Kws i es crea la introducció amb l’API de chatGPT
  4. El contingut creatiu es crea amb l’API de chatGPT. Per això s’usen les dades del Sheet de rol, Kws, cap, to, categories, prompt i substantius
  5. Es crea el contingut final amb l’API de chatGPT explicant per què és important crear aquest contingut creatiu
  6. Creem també la metadescription amb l’API de chatGPT
  7. Creem un prompt per a l’API de LEO tenint en compte els camps rol, cap a i Kw i el guardem en una variable
  8. Generem imatge amb l’API de LEO, obtenim la URL segons l’ID i la pugem a WordPress
  9. Tot el contingut generat per chatGPT es filtra i se substitueixen les etiquetes HTML definides al prompt per les etiquetes amb els comentaris de Gutenberg
  10. El pas 7 ens torna l’ID de la imatge ja pujada al nostre WordPress. És llavors quan podrem crear l’article a WordPress afegint-hi tot el contingut generat:
$post_arr = array(
'post_title'   => $title,

    'post_content' => $final_article,
    'post_status'  => 'publish',
    'post_category' => array('6'),
    'meta_input'   => array(
        '_yoast_wpseo_focuskw'     => $main_kw,
        '_yoast_wpseo_metadesc' => $answer_meta,
    )
);

$post_id = wp_insert_post($post_arr);
$featured = set_post_thumbnail( $post_id, $featured_id );

Aplicació a Python per a publicació automàtica diària a WordPress

Encara que el plugin anterior podria haver-lo creat amb Python i potser hagués estat fins i tot més senzill, em vaig decidir per fer-ho tot a WordPress sense haver de recórrer a eines externes.

Per crear una aplicació que publiqui de manera programada de la manera que jo volia he hagut de recórrer a l’ús de tecnologies externes. En aquest cas he fet servir un NAS, un script de Python que puja les dades mitjançant la REST API de WordPress i la programació de la tasca al NAS mitjançant BASH.

Comparteixo el codi del fitxer de control d’aquesta aplicació:

import openai
import base64
import requests
import json
import pandas as pd
from datetime import datetime
from datetime import timedelta
import sendinblue as sb
import get_img_leo as leo
import up_img_wp as up_img

#df = pd.read_csv('../py/articulos2.csv', usecols=[i for i in range(0,3) ], encoding="ISO-8859-1", sep=';')
sheet_url = 'https://docs.google.com/spreadsheets/d/iDdeNuEstroGoogleSHeeT/edit#gid=0'
url_1 = sheet_url.replace('/edit#gid=', '/export?format=csv&gid=')
df = pd.read_csv(url_1)
today = datetime.today().date()
two_days = today + timedelta(days=2)

two_days_article = 0
counter = 0

for date in df['date']:
    try:
        #print(titulo)
        sheet_date = datetime.strptime(date, "%d-%m-%y").date()
        #check if today has article to post

        if sheet_date == today:

            #img leo
            prompt_leo = df['img'][counter]
            img_leo = leo.img_gen_leo(prompt_leo, 448, 352)

            #upload the image
            img_uploaded = up_img.restImgUL(img_leo)
            img_json = json.loads(img_uploaded)
            img_id = str(img_json['id'])
            img_url = img_json['guid']['raw']

            img_code = '<!-- wp:group {"layout":{"type":"constrained"}' + '} -->\n<div class="wp-block-group"><!-- wp:image {"align":"right","id":' + img_id + ',"sizeSlug":"full","linkDestination":"none"} --><figure class="wp-block-image alignright size-full"><img src="' + img_url + '" alt="imagen impactante para web de piercings" class="wp-image-' + img_id + '"/></figure><!-- /wp:image -->'

            #create post
            openai.api_key = "APIKEY de OPENAI"
            titulo = df['title'][counter]

            #Titulo
            MODEL = "gpt-4"
            response = openai.ChatCompletion.create(
                model=MODEL,
                messages=[

                    {"role": "system", "content": "Eres una experta en copy y redacción para webs de [lo que queramos]"},
                    {"role": "user", "content": "Reescribe el siguiente título, con menos de 60 caracteres, y enfócate en hacerlo lo más atractivo posible: " + str(titulo)},
                ],
                temperature=0.7,
            )

            resp_titulo = response.choices[0].message["content"]
            resp_titulo = resp_titulo.replace('"', '')
            #metadescription
            MODEL = "gpt-4"

            response_meta = openai.ChatCompletion.create(
                model=MODEL,
                messages=[
                    {"role": "system", "content": "Eres una experta en copy y redacción para webs de [lo que queramos]"},
                    {"role": "user", "content": "Escribe una metadescription que no supere los 130 caracteres para un artículo llamado: " + str(titulo)},
                ],
                temperature=0.7,
            )

            metadescription = response_meta.choices[0].message["content"]
            #sections
            MODEL = "gpt-4"

            response = openai.ChatCompletion.create(
                model=MODEL,
                messages=[

                    {"role": "system", "content": "Adopta el rol de copywriter profesional especializada en el mundo de [lo que queramos] y devuelve lo que se te solicite en un único párrafo separando las unidades por comas y sin incluir el titulo"},

                    {"role": "user", "content": "Escribe solamente los títulos de las 5 secciones principales y más relevantes que debería llevar el artículo dirigido a [lo que queramos] con titulo: " + str(titulo)},
                ],
                temperature=0.7,
            )
            sections = response.choices[0].message["content"]

            #content
            MODEL = "gpt-4"

            response = openai.ChatCompletion.create(
                model=MODEL,

                messages=[
                    {"role": "system", "content": "Eres una experta en copy y redacción para webs de [lo que queramos]"},
                    {"role": "system", "content": "Debes crear el contenido en pequeños párrafos para facilitar la lectura"},
                    {"role": "system", "content": "Es vital que el contenido no sea reiterativo ni repetitivo"},
                    {"role": "system", "content": "Debes ser respetuosa en todo momento"},
                    {"role": "user", "content": "Genera un artículo completo en HTML incluyendo exclusivamente las etiquetas: <section>, <h2>, <h3>, <p>, <ul>, <li>, <strong>. Excluyendo etiquetas HTML <h1>. El artículo debe contar con un mínimo de 800 palabras y tiene el titulo '" + resp_titulo + "'. Se deben incluir secciones y subsecciones. El contenido de las secciones no debe ser reiterativo ni repetitivo, las secciones deben ser las siguientes: " + sections + ". Debe ser interesante para el usuario, con una jerarquía de encabezados, H2 y H3 en HTML, así como algún listado ul, acaba todas las frases aunque el texto se exceda del máximo. En este artículo se deben responder las principales dudas que tienen los usuarios en Google sobre este tema concreto, es decir, se deben responder sus preguntas frecuentes. Este artículo solo debe abarcar el tema concreto del que trata el título " + resp_titulo + ", sin abarcar temáticas más generales, aunque estén directamente relacionadas con ese título."},

                ],
                temperature=0.7,
            )

            summary = response.choices[0].message["content"]
            summary = summary.replace('"', '')
            summary = summary.replace('<section>', '<!-- wp:group {"layout":{"type":"constrained"}} --> <div class="wp-block-group">')
            summary = summary.replace('</section>', '</div> <!-- /wp:group -->')
            summary = summary.replace('<p>', '<!-- wp:paragraph --><p>')
            summary = summary.replace('</p>', '</p><!-- /wp:paragraph -->')
            summary = summary.replace('<ul>', '<!-- wp:list --> <ul>')
            summary = summary.replace('</ul>', '</ul> <!-- /wp:list -->')
            summary = summary.replace('<li>', '<!-- wp:list-item --> <li>')
            summary = summary.replace('</li>', '</li> <!-- /wp:list-item -->')
            summary = summary.replace('<h2>', '<!-- wp:heading --> <h2 class="wp-block-heading">')
            summary = summary.replace('</h2>', '</h2> <!-- /wp:heading -->')
            summary = summary.replace('<h3>', '<!-- wp:heading {"level":3} --> <h3 class="wp-block-heading">')
            summary = summary.replace('</h3>', '</h3> <!-- /wp:heading -->')
            summary = summary.replace('</header>', '')
            summary = summary.replace('<header>', '')
            summary = summary.split('<body>', 1)[1]
            summary = summary.split('</body>', 1)[0]
            summary = img_code + summary

            login = 'Alvaro Torres'

            password = 'Clave de Rest API de WordPress'
            url = 'https://nuestraweb.com/wp-json/wp/v2/posts'
            headers = {
                'Authorization': 'Basic ' + base64.b64encode(f"{login}:{password}".encode()).decode(),
                'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; rv:91.0) Gecko/20100101 Firefox/91.0'
            }

            data = {
                'title': resp_titulo,
                'content': summary,
                'featured_media': img_id,
                'status': 'publish',
                'meta': {
                    '_yoast_wpseo_metadesc': metadescription
                }
            }

            response = requests.post(url, headers=headers, json=data)
            post_json = json.loads(response)
            post_id = post_json['id']
            post_url = post_json['guid']['raw']

            if response.status_code != 201:
                print(response.status_code)
                print('Error al crear el post')

        if sheet_date == two_days:
            two_days_article += 1

    except Exception:
        print("Error general")

    counter += 1

if two_days_article == 0:
    sb.send_mail('Configure the article', '[nuestra web] Articles needs to be configured.\n <a href="https://docs.google.com/spreadsheets/d/NuestRoGooGleSheets/edit#gid=0">CLICK HERE</a>', '2 days left to finish configured articles', 'alvaro@mimail.com', 'Alvaro')

Si voleu fer-lo servir haureu de modificar el vostre Google Sheet, la clau de l’API d’Openai, el vostre mail, substituir [el que vulguem] per les dades del vostre projecte i les dades de REST API del vostre web.

També haureu vist que s’importen 2 mòduls que no us sonaran:

import get_img_leo as leo
import up_img_wp as up_img

En realitat són els dos fitxers on he emmagatzemat les classes de chatGPT i Leonardo.ai.

Tots els fitxers els he desat en una carpeta d’un NAS i després he creat una tasca que executa el fitxer principal mitjançant una simple ordre BASH:

cd /
cd volume1/Python/miproyecto
source env/bin/activate
python control_archivo_python.py

Repeteixo, si algú es queda amb dubtes només m’haurà d’escriure per LinkedIn i encantat estaré d’ajudar-lo en el que pugui.

Conclusió

Aquest ha estat un projecte en què he invertit molt de temps, sobretot a nivell de planificació. Però cal tenir en compte que per als següents projectes ja tinc la meitat de la feina feta.

Els resultats estan sent millors del que s’esperava, i encara que això no garanteixi l’èxit real del projecte, sí que sóc força optimista. Això sí, les tècniques de monetització no es basaran exclusivament en publicitat o posts patrocinats, sinó que inclouré un servei força econòmic que estic convençut que pot funcionar.


Álvaro Torres, a més de portar molts anys fent call en el desenvolupament web, és el fundador de WebHeroe, una agència de desenvolupament web especialitzada en personalització a WordPress. Es defineix com un friqui de WordPress a qui li encanta estrènyer-se els cervells per crear nous projectes digitals que li compliquin la vida una mica més.

Resumidament, som uns techies apassionats per WordPress que hem creat Wetopi, un Hosting WordPress Gestionat, per minimitzar la fricció a la que tot professional s’enfronta en treballar i allotjar projectes WordPress.

Inclou servidors de desenvolupament Gratis.
No cal tarjeta de crèdit.

Compara Wetopi amb el teu hosting actual

Dóna’t d’alta, demana una migració i compara.

Sense cap compromís ni esforç per part teva, migrem una còpia del teu web.

Sense lletra petita.
Sense compromisos.
Sense targeta de crèdit.