-
Posts
306 -
Joined
-
Last visited
-
Days Won
8
Everything posted by nbcommunication
-
Wondering how to get that A+ rating on Mozilla Observatory? Now you can with ⭐⭐⭐MarkupContentSecurityPolicy⭐⭐⭐ Of course, MarkupContentSecurityPolicy does not guarantee an A+ rating, but it does help you implement a Content Security Policy for your ProcessWire website. Markup Content Security Policy Configure and implement a Content Security Policy for all front-end HTML pages. This module should only be used in production once it has been fully tested in development. Implementing a Content Security Policy on a site without testing will almost certainly break something! Overview Website Security Auditing Tools such as Mozilla Observatory will only return a high score if a Content Security Policy is implemented. It is therefore desirable to implement one. A common way of adding the Content-Security-Policy header would be to add it to the .htaccess file in the site's root directory. However, this means the policy would also cover the ProcessWire admin, and this limits the level of security policy you can add. The solution is to use the <meta> element to configure a policy, for example: <meta http-equiv="Content-Security-Policy" content="default-src 'self'; img-src https://*; child-src 'none';">. MarkupContentSecurityPolicy places this element with your configured policy at the beginning of the <head> element on each HTML page of your site. There are some limitations to using the <meta> element: Not all directives are allowed. These include frame-ancestors, report-uri, and sandbox. The Content-Security-Policy-Report-Only header is not supported, so is not available for use by this module. Configuration To configure this module, go to Modules > Configure > MarkupContentSecurityPolicy. Directives The most commonly used directives are listed, with a field for each. The placeholder values given are examples, not suggestions, but they may provide a useful starting point. You will almost certainly need to use 'unsafe-inline' in the style-src directive as this is required by some modules (e.g. TextformatterVideoEmbed) or frameworks such as UIkit. Should you wish to add any other directives not listed, you can do so by adding them in Any other directives. Please refer to these links for more information on how to configure your policy: https://developer.mozilla.org/en-US/docs/Web/HTTP/CSP https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Content-Security-Policy https://scotthelme.co.uk/content-security-policy-an-introduction/ https://developers.google.com/web/fundamentals/security/csp/ Violation Reporting Because the report-uri directive is not available, when Violation Reporting is enabled a script is added to the <head>which listens for a SecurityPolicyViolationEvent. This script is based on https://developer.mozilla.org/en-US/docs/Web/API/SecurityPolicyViolationEvent and POSTs the generated report to ?csp-violations=1. The module then logs the violation report to csp-violations. Unfortunately, most of the violations that are reported are false positives, and not actual attempts to violate the policy. These are most likely from browser extensions and are not easy to determine and filter. For this reason, there is no option for the report to be emailed when a policy is violated. Instead, you can specify an endpoint for the report to be sent to. This allows you to handle additional reporting in a way that meets your needs. For example, you may want to log all reports in a central location and send out an email once a day to an administrator notifying them of all sites with violations since the last email. Retrieving the Report To retrieve the report at your endpoint, the following can be used: $report = file_get_contents("php://input"); if(!empty($report)) { $report = json_decode($report, 1); if(isset($report) && is_array($report) && isset($report["documentURI"])) { // Do something } } Debug Mode When this is enabled, a range of information is logged to markup-content-security-policy. This is probably most useful when debugging a reporting endpoint. Additional .htaccess Rules To get an A+ score on Mozilla Observatory, besides using HTTPS and enabling the HSTS header, you can also place the following prior to ProcessWire's htaccess directives: Header set Content-Security-Policy "frame-ancestors 'self'" Header set Referrer-Policy "no-referrer-when-downgrade" Installation Download the zip file at Github or clone the repo into your site/modules directory. If you downloaded the zip file, extract it in your sites/modules directory. In your admin, go to Modules > Refresh, then Modules > New, then click on the Install button for this module. ProcessWire >= 3.0.123 is required to use this module.
- 15 replies
-
- 14
-
-
I've been doing a little rejigging of our default htaccess file after yesterday's dev release, and trying to understand Section 18 a bit better too... In section 18 we use a rule based on what is outlined here: https://processwire.com/blog/posts/optimizing-404s-in-processwire/ RewriteCond %{REQUEST_URI} !\.(jpg|jpeg|gif|png|ico|webp|svg|php|cgi|pl|asp|rar|zip)$ [NC] This is entered after the existing section 18 rules, which are left commented out. After the end of ProcessWire's htaccess rules we have: <FilesMatch "\.(jpg|jpeg|gif|png|ico|webp|svg|php|cgi|pl|asp|rar|zip)$"> ErrorDocument 404 "The requested file was not found. </FilesMatch> Without that rule, I get the ProcessWire 404 page when accessing a non-existent file matching one of those types. On a different htaccess-related note, I recommend the 6G htaccess Firewall https://perishablepress.com/6g/. We have this at the start of our default .htaccess file, followed by: ErrorDocument 403 "Sorry, you are not permitted to access this resource. The only issue I've come across after a few years of use is with the autocomplete Page field, when using OR selectors (e.g. template=home|default). I wrote this hook as a remedy: <?php // Replace pipes (|) with %7C in PageAutocomplete data-url attribute // This gets around 6G htaccess rules which disallows pipes in urls $wire->addHookAfter("InputfieldPageAutocomplete::render", function(HookEvent $event) { $out = $event->return; if(strpos($out, "data-url") === false) return; $url = explode("'", ltrim(explode("data-url=", $out)[1], "'"))[0]; $event->return = str_replace($url, str_replace(" ", "+", str_replace("|", "%7C", $url)), $out); }); Cheers, Chris
-
Hey, Launched a site today with a form that sends attachments and it turned out that our production server doesn't have mime_content_type() ? https://github.com/chriswthomson/WireMailMailgun/pull/17 I've added a private method getMimeType() which checks first for mime_content_type(), then finfo_open(), then falls back to inferring based on file extension if neither exist. This is based on https://www.php.net/manual/en/function.mime-content-type.php#87856 and https://gist.github.com/Erutan409/8e774dfb2b343fe78b14#file-mimetype-php Also, a WireException is now thrown if an attachment has been added using WireMail::attachment() but curl_file_create() doesn't exist. Cheers, Chris
-
Hi @Schwab - I'm not sure how this can be done, although given that there are a number of WireMail extension modules out there, I'm sure it must be possible and discussed previously. Might be worth having a look through the threads for WireMail SMTP etc to see if there is any info there. I'm assuming this is @Macrura's version on the module repo - these methods came from the original "plauclair" version. I removed them entirely from my version as they were unnecessary, and didn't look like they would work anyway, given that trackClicks and trackOpens should be booleans (technically integers, but evaluate as either true or false). I updated chriswthomson/WireMailMailgun last week with fallbacks etc, tested on 2.7.2 and above. Ended up moving straight onto another task and completely forgot to post!
-
@Macrura - Thanks for the info. I wasn't thinking outwith explicit calls to WireMailMailgun, so that makes sense. I'll probably still add the setSender() and setRegion() functions though, might be useful to have. Cheers, Chris
-
@jens.martsch - thinking through it a little more, I think the addition of h:sender should only happen if the "from" domain is different to $this->domain. I'll pop that in place soon. I'd wondered whether using this would effect the DKIM auth etc but a few quick tests suggest that it doesn't ?. @Macrura - I've been thinking about the Dynamic Domain setting, which I'd implemented based on your version but didn't give it much thought. Does it actually work without specifying the API key for the different domain? I wonder whether this could be removed and the following be the way to send from a different domain? <?php $mg = $mail->new(); $sent = $mg->to($to) ->setDomainName("mg.differentdomain.com") ->setApiKey($differentApiKey) ->setRegion("eu") // If the region is different //->setSender("mg.differentdomain.com", $differentApiKey, "eu") // Alternative, region optional ->subject($subject) ->bodyHTML($message) ->send(); Cheers, Chris
-
Hi @jens.martsch - I've merged your request. I'd always thought that was the correct behaviour because if you send from a domain that isn't what you have in Mailgun (e.g. @test.com when @mg.test.com is your verified domain) then the "on behalf of" is the correct result. However, if one line fixes that, that's great! Cheers, Chris
-
New blog post: Lots of module updates
nbcommunication replied to ryan's topic in News & Announcements
Much love to you and your family Ryan, haven't had that experience before, and not looking forward to having it in future - cats make a bigger difference to your life than you'd think! Thanks again for all you do. -
Hi, I've added an addInlineImage() method to https://github.com/chriswthomson/WireMailMailgun <?php $img = $pages->get(1)->images->getRandom(); // An example $customFilename = "test.$img->ext"; // Don't want to use the basename for this example $mg = $mail->new(); $mg->to("your@email.com") ->subject("Test Inline Image") ->bodyHTML("<p>Testing, 123, is there an image for you to see?</p><img src='cid:$customFilename'>") ->addInlineImage($img->filename, $customFilename) // Second argument is optional ->send(); If the image isn't referenced in the HTML it just appears as a standard attachment from what I can see. Cheers, Chris
-
Having a look at https://documentation.mailgun.com/en/latest/api-sending.html#sending inline is a separate parameter that would need to be implemented. I’ll have a look at this on Monday when I’m back at the coalface. ? Chris
-
Agreed. I think that perhaps the best solution is for you to maintain the module, integrating anything applicable from my version. I’d be happy to help with this process.
-
I’m not really sure to be honest - I haven’t added anything to the directory before so will need to have a look through the process. A couple of points: - is it acceptable/desirable to have a module that’s only compatible with the lastest master (123) and beyond? - ProMailer: I’ve not looked at this myself, and don’t expect to in the near future. My assumption is that Ryan has developed this to be compatible with the initial WireMailMailgun, which has differences in batchMode for cc/bcc - maybe this wouldn’t be an issue at all, I don’t know. I guess what I’m trying to say is that I’d be delighted to add it to the directory, but feel that the original should be retained. Perhaps the new version should be renamed? WireMailMailgun3? Cheers, Chris
-
Hi @adrian, A lot of the code is much the same, but tidied up with the the coding style guide implemented, so I'm not surprised the diff doesn't reveal much! The readme is pretty thorough and covers a lot, but here's the gist: addData() - add X-Mailgun-Variables - https://documentation.mailgun.com/en/latest/user_manual.html#attaching-data-to-messages - to be honest don't know what use cases there are for it but it's in the API and was easy to implement addTags() - add multiple tags as an array getHttpCode() - to get the response code from either send() or validateEmail() * Most methods now chainable (see the Advanced Example in the readme) Tracking only used if bodyHTML() is set (As this only works in HTML email) cc() and bcc() only used when batchMode is off - this seems to me to be the correct implementation WireMail::htmlToText() used for generating the text version if only HTML passed (as in WireMail now) The ASCII conversion for tags now uses $this->sanitizer->nameFilter($tag, [" "], "", false, 128); WireMail::replyTo() implemented - doesn't seem to have been before removed addAttachment(), now uses WireMail::attachment() - which adds the ability to set the filename Unixtime is now passed to setDeliveryTime() A bunch of other small tweaks like using $sanitizer->email() in validateEmail() * I'd wanted to use WireHttp for the requests, but it doesn't allow custom cURL options. I have done a pull request for this, but I don't think I'll be changing the module's cURL request implementation now anyway. Cheers, Chris
-
Hello, We've been using Mailgun for several years now on ProcessWire developments, using a cURL implementation within a custom site development module/template site. I'm currently rewriting that and trying to use much more of the PW API as there's been a lot of handy things added in the past while. Part of that process is to use WireMailMailgun, so I installed @Macrura's fork and then began to see what could be improved/finished off from the todos. What I've ended up doing is a partial rewrite of the module: to use more ProcessWire conventions and the coding style guide implemented a few extra features removed what I though was unnecessary code. It requires 3.0.123 and above, as it uses the htmlToText() method from WireMail, which in turn uses WireTextTools. The module is here: https://github.com/chriswthomson/WireMailMailgun Please let me know your thoughts! Cheers, Chris
-
Hi suntrop, My best guess is that the error is occurring before PW has determined that you are logged in. I'm pretty sure the PW error message is only displayed to logged in users - that's my experience anyway! Cheers, Chris NB
-
Thinking about this further, the label method wouldn't be required if uk-text-[status] classes were employed. e.g: .uk-text-success was a bit faint compared to .uk-text-primary hence why this is used. Cheers, Chris NB
-
Hi Ryan, Love the page tree customisation additions! I've got a request that I think would be pretty useful, which is to add the ability to break the count down by page status eg: News 40/2/5 Where the numbers represent published/hidden/unpublished. In the case of all published pages, it would just display the child count. It might also make sense for an option to display a label eg: News 40 published / 2 hidden / 5 unpublished or News 40 published / 5 unpublished This might not look that great if all rootParents have children of varying statues, but still worth having the option. If there's a better place to put this request, please let me know! I'm getting pretty familiar with the core, but don't know enough about how the admin theme works to be able to prototype and pull request it. Thanks as ever for ProcessWire and all your continuing work. Cheers, Chris NB
-
Hi, There's a couple of display issues with this on the new UIkit theme. I managed to fix this by adding a css file to $config->styles (in admin.php) with the following: .InputfieldColorPicker ul { margin: 0; padding: 0; } .InputfieldColorPicker ul li { list-style: none; } Cheers, Chris
-
Hi, With the introduction of GDPR regulations, many of our clients with "webuser" systems we've developed need a way to email users that haven't logged-in in a while (18 months seems to be the standard) to ask them if they still want their user account. For most of the systems we've developed, we've added a field to the user template which records the time when the user logs in, so we'll be able to develop this functionality. It got me thinking, would this be a welcome addition to the core, accessed in a similar way to created/modified dates e.g. $user->lastlogin? Were it to be implemented, it would be useful to be able to 'silently login' if using $session->login($username, $pass) or $session->forceLogin($username), in the same way you can bypass save hooks by passing in an option to $pages->save(). Cheers, Chris - NB Communication
- 8 replies
-
- 10
-
-
Windows IIS Server - recurring Class not found errors
nbcommunication replied to nbcommunication's topic in General Support
Hi matjazp, Unfortunately I don't have access to logs, basically just a file browser from a simpler time... The web.config was just hobbled together from various bits and pieces I found, although mainly based on one person's work for a 2.5 install on IIS I think - I wish I could remember who it was/where I found it. Anyway, that should be attached... The errors started happening again last night (Class 'ProcessWire\Pagefile' not found) but only lasted for 15 minutes that then stopped. Totally weird, totally frustrating, and I'm almost 100% sure it's totally not the fault of PW too! Cheers, Chris sample.web.config -
Hi, We recently launched a PW site (3.0.62) on the client's own Windows IIS server. After a bit of research on the forums and some back and forth with their IT team, I got the site running, with ProCache too. Twice in the past month the site has gone down, due to a really peculiar error. It's as if PW can no longer find files on the server even though they are still there. Here's an error from today: Page: http://www.sitedomain.org/http404 User: guest Error: Uncaught Error: Class 'ProcessWire\PageAccess' not found in C:\Websites\sitedomain\admin\files\web\wire\core\Page.php:3666 Stack trace: #0 C:\Websites\sitedomain\admin\files\web\wire\core\Page.php(3688): ProcessWire\Page->getHelperInstance('PageAccess') #1 C:\Websites\sitedomain\admin\files\web\wire\core\Page.php(3566): ProcessWire\Page->access() #2 C:\Websites\sitedomain\admin\files\web\wire\core\Page.php(3276): ProcessWire\Page->getAccessTemplate() #3 C:\Websites\sitedomain\admin\files\web\wire\core\Page.php(3265): ProcessWire\Page->___isPublic() #4 C:\Websites\sitedomain\admin\files\web\wire\core\PagefilesManager.php(481): ProcessWire\Page->isPublic() #5 C:\Websites\sitedomain\admin\files\web\wire\core\PagefilesManager.php(343): ProcessWire\PagefilesManager::_path(Object(ProcessWire\Page)) #6 C:\Websites\sitedomain\admin\files\web\wire\core\PagefilesManager.php(328): ProcessWire\PagefilesManager->___path() #7 C:\Websites\sitedomain\admin\files\web\wire\core\PagefilesManager.php(268): ProcessWire\PagefilesManager->path() #8 C:\Websites\sitedomain (line 3666 of C:\Websites\sitedomain\admin\files\web\wire\core\Page.php) The first time it happened it wasn't the 404 page, and it was TextformatterVideoEmbed that seemed lost. This then developed into other, more important, files not being found (Uncaught Error: Class 'ProcessWire\RepeaterPageArray' not found). I tried refreshing the module cache and clearing complied files (I think I even cleared the cache folder completely) and permissions seem fine. The first time it happened the client's IT team restarted their server and the problem was resolved. They couldn't see anything in the logs, nor had they made a change to the server. There doesn't seem to be a trigger for it happening either. Does anyone here have any experience with running PW on Windows IIS, and/or have any ideas why this may be happening? Cheers, Chris
-
Inline image bug as of CKEditor update
nbcommunication replied to nbcommunication's topic in General Support
Update: I downloaded/installed a fresh copy of 3.0.62 and the same thing is happening, although only when using Inline mode. Regular mode works fine. I've submitted an issue on Github: https://github.com/processwire/processwire-issues/issues/279 Cheers, Chris- 1 reply
-
- 1
-
-
Hi, Just had a client in touch to say that whenever they try to add an image into a content area (CKEditor Textarea) it always puts the image to the top. I've tested this on installs using various admin themes and the same thing is happening for me. Is anyone else getting this bug? Assuming it is likely to do with the update to CKEditor (which is lovely :D) Cheers, Chris
-
$pages->sort($parent, true) bug?
nbcommunication replied to nbcommunication's topic in General Support
Stack trace from the second example, which I called on the 404 page... Error: Exception: SQLSTATE[HY000]: General error: 1364 Field 'name' doesn't have a default value (in ../wire/core/PagesEditor.php line 1388) #0 ../wire/core/PagesEditor.php(1388): PDOStatement->execute() #1 ../wire/core/Pages.php(882): ProcessWire\PagesEditor->sortRebuild(Object(ProcessWire\Page)) #2 ../wire/core/Wire.php(386): ProcessWire\Pages->___sort(Object(ProcessWire\Page), true) #3 ../wire/core/WireHooks.php(698): ProcessWire\Wire->_callMethod('___sort', Array) #4 ../wire/core/Wire.php(442): ProcessWire\WireHooks->runHooks(Object(ProcessWire\Pages), 'sort', Array) #5 /home/stmasway/public_html/site/templates/404.php(9): ProcessWire\Wire->__call('sort', Array) #6 ../wire/core/TemplateFile.php(268): require('/home/stmasway/...') #7 ../wire/core/Wire.php(380): ProcessWire\TemplateFile->___render() #8 ../wire/core/WireHooks.php(698): ProcessWire\Wire->_callMethod('___render', Array) #9 ../wire/core/Wire. -
Hi, I was adding a hook in admin.php which updates a field that is based on the sort value and runs after Pages::sorted. Looking through the docs, I figured hey I'll run $pages->sort($parent, true) so that the sort values are correct before setting the other field. Here's the basic hook: <?php namespace ProcessWire; $pages->addHookAfter("Pages::sorted", function($event) { $pages = $event->object; $page = $event->arguments(0); $pages->sort($page->parent, true); // Other stuff return; }); This kept returning the following exception: SQLSTATE[HY000]: General error: 1364 Field 'name' doesn't have a default value (in .../wire/core/PagesEditor.php line 1388) Now, thinking through this, sorting the pages in the admin probably runs the sortRebuild() function that the error is referring to anyway, so $pages->sort($parent, true) isn't needed at all and perhaps this is why the error is appearing. However, I've just run <?php namespace ProcessWire; if($user->hasRole("superuser")) { $pages->sort($pages->get(1072), true); } And this is returning the same error/exception. The parent called above has 14 child pages. Running 3.0.62. Is this something I'm doing wrong? Cheers, Chris NB Communication