Jump to content

Neue Rituale

Members
  • Posts

    35
  • Joined

  • Last visited

  • Days Won

    1

Posts posted by Neue Rituale

  1. @Gideon So

    Yes, the module requires PHP version 7.4 or higher. I will show that more transparently in the next version.

    You could replace the line with this one  private $essence = null;.
    But I think there will be more incompatibilities to php@7.1.

  2. Thanks for the great modules. Maybe this was answered, unfortunately I didn't find anything about it.
    How can I remove or overwrite the routes from "DefaultRoutes.php"? I have already tried it with this:

    $module = $this->wire('modules')->get('AppAPI');
    $module->registerRoute(
    	'auth', [
    		['OPTIONS', '', AppApiHelper::class, 'noEndPoint'],
    		['GET', '', AppApiHelper::class, 'noEndPoint'],
    		['POST', '', AppApiHelper::class, 'noEndPoint'],
    		['DELETE', '', AppApiHelper::class, 'noEndPoint'],
    	]
    );

    Unfortunately, they are still accessible and functional.

  3. Quote

    ... So if I used that image url in my websites markup it would generate an external request that violates GDPR if I have no prior consent

    Are you sure? I thought only when personal data is transferred. (e.g. in cookies).

    By the way, here is a basic example of how to store the oembed image in a separate image field. In this example, the field name is "mediaImage". But i think it is a good idea to integrate this as a feature of FieldtypeOembed.

    Spoiler
    // If media and no preview image exists
    if(
    	$page->template->name === 'media' &&
    	$page->id &&
    	($page->mediaImage instanceof Pageimages && $page->mediaImage->count() === 0) &&
    	!empty($page->mediaEmbed)
    ) {
    
    	// get data from db
    	// return if no oembed data found
    	$mediaEmbed = $this->pages->getRaw('id=' . $page->id, ['mediaEmbed'])['mediaEmbed'] ?? null;
    	$oembed = json_decode($mediaEmbed['oembed'], JSON_OBJECT_AS_ARRAY);
    	if(!$oembed || !(is_array($oembed) && array_key_exists('thumbnailUrl', $oembed))) return;
    
    	// get field
    	/** @var FieldtypeImage|FieldtypeFile $mediaImageField */
    	$mediaImageField = $page->getField('mediaImage');
    	$allowedExtensions = explode(' ', $mediaImageField->extensions);
    
    	// build filename form oembed data, merge and sanitize
    	$filename = array_filter(array_intersect_key($oembed, array_flip(['title', 'providerName', 'type'])));
    	if(!count($filename)) $filename[] = 'thumbnail';
    	$filename = $this->sanitizer->snakeCase(strtolower( implode(' ', $filename) ));
    
    	// download file and save in tmp folder
    	$fileContent = $this->files->fileGetContents($oembed['thumbnailUrl']);
    	$tempDir = $this->files->tempDir();
    	$path = $tempDir->get();
    	$pathToFile = $path . $filename;
    	$tmpFile = $this->files->filePutContents($pathToFile, $fileContent);
    	if(!$tmpFile) throw new Exception('Thumbnail file is empty');
    
    	// find extension by mime type and check if is allowed in this field
    	$internalFileExtensionFromMimeType = strtolower(explode('/', mime_content_type($pathToFile))[1] ?? 'unknown');
    	if(!in_array($internalFileExtensionFromMimeType, $allowedExtensions)) throw new Exception("Invalid internal filetype, \"$internalFileExtensionFromMimeType\" now allowed");
    
    	// add mime type file extension to filename
    	if(!$this->files->rename($pathToFile, $pathToFile . '.' . $internalFileExtensionFromMimeType)) throw new Exception("Error while renaming file ($filename)");
    	$pathToFile = $pathToFile . '.' . $internalFileExtensionFromMimeType;
    
    	// add file to page
    	$page->of(false);
    	$page->mediaImage->add($pathToFile);
    	$page->save('mediaImage');
    }

    This code can be called in a Page::saveReady Hook with $page = $event->arguments(0);

    • Like 1
  4. Quote

    I either don't agree or don't understand. But I guess it means that the module does not provide any helpers to make the embedding comply with gdpr and that is something that the developer needs to take care of?

    Yes, the developer needs to take care of it.

    We use it in different ways. One variant works with the template tag. For this, the content from `html` is wrapped in a `<template>` tag. Instead of the content, a message is displayed that refers to the external content of its respective provider. After clicking, the content of the template tag is appended into the DOM with JavaScript.

    Here is an example: https://koerber-stiftung.de/en/projects/the-berlin-pulse/highlight-the-berlin-pulse-digital-tools-give-repressive-governments-the-upper-hand/#s18430

    Another way is to insert the `html` (iframe) of videos (Youtube or Vimeo) via the nocookie domain or with dnt=1 parameter into Plyr. The embed data can also be used to configure the video player and placeholder (poster image, duration, aspect ratio).

    The click on the play button is then also the consent. Data is then also sent via the "normal" youtube domain. The advantage of this method is that it only requires one click (trusted click) because the html is already initialised.

    https://koerber-stiftung.de/mediathek/debattle-das-wortgefecht-4/

    Another feature is you can find pages by OEmbed properties like:`$pages->find('my-embed-field.providerName=YouTube')`

     

    • Like 1
  5. Maybe this can help. It work like the original `$datetime->formatDate()` Method.

    wire()->addHookMethod('WireDateTime::formatIntlDate', function(HookEvent $event) {
    
    	$value = $event->arguments(0);
    	$format = htmlspecialchars_decode($event->arguments(1), ENT_QUOTES); // support placeholder in time format like 'o''clock'
    
    	if(!$value) { $event->return = ''; return; }
    	if(!strlen("$format")) { $event->return = (int) $value; return; } // unix timestamp
    
    	// create datetime
    	$dt = \DateTime::createFromFormat('U', (int) $value);
    	if(!($dt instanceof \DateTime)) { $event->return = (int) $value; return; }
    
    	// set timezone
    	if($this->config->timezone) $dt->setTimezone(new \DateTimeZone($this->config->timezone));
    
    	// locale
    	$locale = setlocale(LC_TIME, 0);
    
    	// format
    	$event->return = \IntlDateFormatter::formatObject($dt, $format, $locale);
    });
    
    echo $datetime->formatIntlDate(1678010433, \IntlDateFormatter::LONG);
    // March 5, 2023 at 11:00:33 AM GMT+1 (en_US)
    // 5 March 2023 at 11:00:33 CET (en_GB)
    // 5. März 2023 um 11:00:33 MEZ (de_DE)
    
    echo $datetime->formatIntlDate(1687453200, __("ccc, d. MMM y hh:mm a"));
    // Thu, 22. Jun 2023 07:00 PM (en_US)
    // Translated in German: "ccc, d. MMM y kk:ss 'Uhr'"
    // Do, 22. Juni 2023 19:00 Uhr (de_DE)

    You can find all date field symbols here: https://unicode-org.github.io/icu/userguide/format_parse/datetime/#date-field-symbol-table

  6. The module provides a list of PageTable based content elements. It enables the backend user to easily create, publish, move, delete, copy and paste content elements.

    The rendering logic of the module is detached from the ProcessWire backend scope via Shadow DOM and allows the elements rendering identical to the front end. It ships with some helper functions that simplify the handling of content elements.

    Download/Install
    Github: https://github.com/neuerituale/PageTableNext
    Module directory: https://processwire.com/modules/page-table-next/
    Composer: composer require nr/pagetablenext

    • Like 13
  7. Hi Guys,

    i want to get a hooked page property into my graphql schema. Does anybody know how i can configure/implement this?

    /* the examble from https://processwire.com/docs/modules/hooks/#how-can-i-add-a-new-property-via-a-hook */
    wire()->addHookProperty('Page::intro', function($event) {
      $page = $event->object;
      $intro = substr(strip_tags($page->body), 0, 255);
      $lastPeriodPos = strrpos($intro, '.');
      if($lastPeriod !== false) $intro = substr($intro, 0, $lastPeriodPos);
      $event->return = $intro;
    });

    I am playing around with the getQueryFields-Hook but I don't know what to do next:

    wire()->addHookAfter('ProcessGraphQL::getQueryFields', function ($event) {
    
    	$types = $event->return;
    	foreach($types as $type) {
    		if($type['name'] === 'mytype') {
    			/** @var ObjectType $pageType */
    			$pageType = $type['type']->getField('list')->getType()->getOfType();
    			$fields = $pageType->getFields();
    			
    			// ????
    			// and here i will add some fields
    		}
    	}
    
    	$event->return = $types;
    });

     

  8. Retrieve, collect and store geolocation data from external geocoding services. Under the hood, the module uses the great PHP Library geocoder-php by William Durand and Tobias Nyholm and adds some processwire magic.

    Download/Install
    Github: https://github.com/neuerituale/FieldtypeGeocoder
    Module directory: https://processwire.com/modules/fieldtype-geocoder/
    Composer: composer require nr/fieldtypegeocoder

    v.1.0.1
    - Add support for GraphQL-Module by dadish

    v.1.0.2
    - Support Repeater

    v.1.0.3
    Add support for bitwise status search.

    v.1.0.4
    - Fix php 8.2 warning #3 
    - Update composer file
    - Update leaflet version
    - Add short access to coordinates

    • Like 6
  9. Store, collect and update oembed data from external sources. This module uses the great PHP Library Essence by Félix Girault and adds some processwire magic. It is inspired by Ryan's example module FieldtypeEvents and the TextformatterOEmbed module by felixwahner. Thanks!

    Download & Install
    Github: https://github.com/neuerituale/FieldtypeOembed
    Modules directory: https://processwire.com/modules/fieldtype-oembed/
    Composer: composer require nr/fieldtypeoembed

    • Like 15
×
×
  • Create New...