Package: websauna.newsletter
This is a newsletter addon forWebsauna framework. It is intended for automatic newsletter generation from the site content.FeaturesInstallationInstalling Python packageSetup newsletter rendererUnsubscription linkSetting up the secretsCreate Mailgun mailing list objectIntegration subscription for on your siteUsageSending and previewResetting the news collection dateExporting subscribersImporting email subscribersLocal development modeRunning the test suiteManually testing with CeleryTODOMore informationChangelog for Websauna Newsletter1.0a3 (2018-10-03)1.0a2 (2018-04-22)1.0a1 (2018-03-06)FeaturesAutomatic newsletter generation from site contentAdmin interface for newsletter preview and sendImport all site users as newsletter subscribersOutbound email throughMailgunUnsubscribe management through MailgunRedis based newsletter state management (when the last letter went out, etc.)Websauna’s Celery based task subsystem is used to run long running operations asynchronouslyInstallationTo run this package you need Python 3.4+, PostgresSQL and Redis.You need to provide your own site-specific INewsletter implementation that populates the news letter content.Installing Python packageInstall this package usingpip.Setup newsletter rendererYou need to register a site specific newsletter that is responsible for rendering your newsletter HTML payload. Do this in yourInitializer.configure_views. Example:# Configure newsletter rendererfrommysite.views.newsletterimportNewsletterRendererfromwebsauna.newsletter.interfacesimportINewsletterGeneratorregistry=self.config.registryregistry.registerAdapter(factory=NewsletterRenderer,required=(IRequest,),provided=INewsletterGenerator)For more information seedemo.py.Unsubscription linkIn your renderer HTML code you can use Mailgun unsubscription management:<pclass="details">{# For Mailgun #}<ahref="%mailing_list_unsubscribe_url%">Unsubscribe from TokenMarket newsletter.</a></p>Setting up the secretsAdd Mailgun API keys and such inmyapp/conf/development-secrets.ini.Example:[mailgun]# Get from Mailgunapi_key=x# What is the mailing list we use in the test suitemailing_list=unit-testing@mailgun.websauna.org# Outbound domain used for the newsletteringdomain=mailgun.websauna.org# From: email we use to send the newsletterfrom=MyApp Newsletter <newsletter-demo@websauna.org>Create Mailgun mailing list objectEasiest to do this throughws-shellusing production configuraition:ws-shell tokenmarket/conf/production.iniThen using%cpastenotebook shell command:from websauna.system.core.utils import get_secrets
from websauna.newsletter.mailgun import Mailgun
secrets = get_secrets(request.registry)
list_address = secrets["mailgun.mailing_list"]
mailgun = Mailgun(request.registry)
mailgun.create_list(list_address, "MyApp newsletter")You get a reply:{'list': {'access_level': 'readonly',
  'address': 'newsletter@example.com',
  'created_at': 'Wed, 25 Jan 2017 17:08:56 -0000',
  'description': 'TokenMarket newsletter',
  'members_count': 0,
  'name': ''},
 'message': 'Mailing list has been created'}Integration subscription for on your siteA boostrap based mini subscription form is provided with the packag. It is ideal e.g. to place in the site footer.Simply in your template do:<h3>Follow</h3>
{% include "newsletter/subscription_form.html" %}For more information run the demo and viewdemotemplates/site/footer.html.UsageSending and previewVisitNewslettertab in the admin interface to preview and send out newsletters.Resetting the news collection dateYou can manually set the newsletter state, when the last newsletter was sent, from shell:importdatetimefromwebsauna.newsletter.stateimportNewsletterStatestate=NewsletterState(request)state.set_last_send_timestamp(datetime.datetime(2016,12,24).replace(tzinfo=datetime.timezone.utc))State is managed in Redis.Exporting subscribersIn console:fromwebsauna.system.core.utilsimportget_secretsfromwebsauna.newsletter.mailgunimportMailgunsecrets=get_secrets(request.registry)list_address=secrets["mailgun.mailing_list"]mailgun=Mailgun(request.registry)print(mailgun.list_members(list_address))# TODO: paginationImporting email subscribersNote that importing website users is supported in the admin interface.Example:subscribers="""
mikko@example.com
pete@example.com
"""fromwebsauna.system.core.utilsimportget_secretsfromwebsauna.newsletter.mailgunimportMailgunfromwebsauna.newsletter.viewsimportsubscribe_emailsecrets=get_secrets(request.registry)list_address=secrets["mailgun.mailing_list"]mailgun=Mailgun(request.registry)forsinsubscribers.split():s=s.strip()ifs:subscribe_email(request,s)Local development modeYou can development this addon locally.Activate the virtual environment of your Websauna application.Then:cd newsletter  # This is the folder with setup.py file
pip install -e .
psql create newsletter_dev
ws-sync-db  ws://websauna/newsletter/conf/development.ini
pserve  ws://websauna/newsletter/conf/development.ini --reloadRunning the test suiteFirst create test database:# Create database used for unit testing
psql create newsletter_testInstall test and dev dependencies (run in the folder withsetup.py):pip install -e ".[dev,test]"Run test suite using py.test running:py.testManually testing with CeleryMake sure Celery is not eager indevelopment.ini:websauna.celery_config =
    {
        "broker_url":  "redis://localhost:6379/15",
        "task_always_eager": False,
    }Start demo (Terminal 1):pserve ws://websauna/newsletter/conf/development.iniStart Celery (Terminal 2):ws-celery  ws://websauna/newsletter/conf/development.ini -- workerTODODouble confirmation to the mailing list subscriptionMore informationPlease seehttps://websauna.org/Changelog for Websauna Newsletter1.0a3 (2018-10-03)After subscription, redirect user back to original url.Support for Python 3.7.1.0a2 (2018-04-22)Fix missing ‘namespace_packages’.1.0a1 (2018-03-06)Initial Release