The requirements for the first alpha release of the 8.x-3.0 series are:
- Have an usable CSV parser UI that operates without errors.
- Have an usable XML parser UI that operates without errors.
- Have a working tamper module with at least one tamper plugin.
Optional:
- Functional tests for the Feeds UI.
The CSV parser UI should be fixed in the Feeds module itself. The other two should be fixed in contrib: the XML parser UI in Feeds extensible parsers and the tamper module in a combination of Tamper and Feeds Tamper. However, it's likely that in order for the XML and tamper requirements to be fixed, changes are needed in Feeds, hence why they are listed here.
The plan
The first thing to complete is the CSV parser UI, because it will define the path for how the XML parser UI should be made. Feeds Tamper's architecture can be developed simultaneously, however it's UI may depend on how the UI for the CSV parser is built.
Tasks
This are the tasks to be done for the first alpha release. The red tasks are required, the yellow tasks are optional.
Comments
Comment #2
megachrizComment #3
larowlanComment #4
dman commentedFrom looking at the prototype/roadmap for 'Tamper' project (NOT feeds_tamper - a confusion that lost me a bit of confusion) ....
I think that the idea for a new, stand-alone 'Tamper" API
> Tamper is a generic API for transforming data
Seems overly broad and ambitious. It (curently) appears abandoned, or at least inactive.
MY feeling is that since that idea (a fine proposal in principle) was put up as a placeholder ...
Better things and tools have become available in the D8/Symfony subsystem.
If we want a generic 'Tamper' facility (do we really, can we really without adding too much extra abstraction?) - I think that the arcitecture seems to be better to leverage the Symfony plugins for event reactions or listeners (sorry, I can't quote the exact terminology, but I have seen tools like this - tools that now stand in for our old D7 hook_x_alter() style events.
I THINK that the concept of relying on the non-existent super-generic vaporware 'tamper' external module is holding up the roll forward of progress in Feeds D8, and should probably be dropped for now.
I BELIEVE that there are other tools somewhere inside the D8 structure already that will be a better fit for this task, and will also be compatable with the D8 style of reacting on events and 'tampering/altering' objects at given phases of processing.
(I can't name-drop those yet, I've only seen them at a distance and my brain is not fresh ATM)
Comment #5
megachriz@dman
You make some valid points here. You are probably right that developing a generic Tamper module first will slow down the progress for Feeds D8. So that is a valid concern for dropping Tamper module for now.
Good to hear also that there already other tools available that provide similar functionality. It would be good to investigate what they are and if it wouldn't take a lot of effort to depend on them. If it does seem to take a lot of effort, we should just go for a more 'simple' port of Feeds Tamper for now.
@dman, would you like to check what these other tools were? I know there is a Typed data API, which I haven't studied yet. Can it be that these tools are somewhere inside that API?
Comment #6
dman commentedTamper with fields via event subscribers
I've gone back to some stuff I was remembering, and also discussed with a few other brains here at DrupalSouth today.
The subsystem I was referring to vaguely is the Symfony EventDispatcher stuff! Sorry I was temporarily drawing a blank on the word when put on the spot for an opinion before.
The Feeds D8 Conceptual Overview even acknowledges 'Events' as the paradigm to shift to. I think we just need to keep doing that, but at a more granular (per-field) level.
Looking at other related things like MigratePreRowSaveEvent, my gut was telling me that what we could be doing is registering a FeedsFieldPrepare event, and then having tampers subscribe to that event and do the altering that they want!
Even if Feeds and Feeds_Tamper is still part of the same project, it's ok for the one module to respond to its own events.
*This*, I feel, provides the abstraction of a 'tamper' opportunity that the proposed 'Tamper' module was envisioning, without introducing additional dependency or layers.
We'll still need a Feeds Tamper UI of sorts to be added to the module, and it'll still have to manage the order of the tampers (apparently Event Dispatching can't be trusted for order-of-operation) but the decoupling of the feeds pipeline into events and listeners seems to be architecturally more the way things are going.
Typed Data as internal row format
You mention typed data API - which, although it has nothing to do with *this* "tamper" question, is also a good suggestion for a standardised middleware data format I'd put forward to @thomasmurphy as they started to discuss the build of the CSV parser and plan the next XML parser.
IF we can trust and use typed_data (I'm not sure it's production-ready yet), Then yeah, I feel like Feeds should be able to return typed_data from its Parser phase, and the Processor should consume typed_data.
A win there is that pre-existing CSV->typed_data, JSON->typed_data, XML->typed_data, remote_api_call->typed_data converter libraries should already exist and become not-our-problem.
Adopting Typed_data for our arbitrarily-formatted imported rows also seems to improve potential compatibility with Rules, which I'm slowly attempting to nudge forwards also.
Comment #7
ericgsmith commentedHi @dman - was good to meet you at DrupalSouth!
I've taken a quick look through this thread although I doubt I have nearly enough information - but here are a few thoughts - apologies if I am polluting this thread as there seem to be similar conversations happening across the 3 modules in question.
I actually quite like the idea of tamper module being decoupled - I think there would be real value in this pattern being abstracted so that eventually feeds and migrate might be able to share more of their code than they can now.
As far as the feeds module goes itself, I think a feeds tamper module can work without any additional events being fired with the existing init and process events currently in use. It could follow the same pattern of dynamically registering event subscribers after the init function fires.
E.g.
Entity structure needed
- we need a config entity of "feed tamper" or something which contains information on what tamper plugins and settings are applied to what field mappings (this would be sort of similar pattern to the entity view mode entity, in that it stores what field formatter plugins and settings are applied to what fields - feeds tamper config entity would do the same just with multiple tamper plugins/settings per mapping)
Processing steps
- feeds tamper subscribes to the feeds.init_import event
- use the feed information supplied to see if we have a relevant tamper configuration entity for the current feed. if we do, dynamically register the feed tamper process method (with a high priority so it runs before feeds process)
- in the process method instantiate the tamper plugins with their settings and call their transforms on the relevant item data. once that has run the regular feeds process will be next in line to run the import.
I don't know enough about the internal dynamics of feeds and how the mapping & storage / processing works at this stage to kick anything off the ground further - although I've as a bit of a playground to the idea added https://github.com/ericgsmith/tamper - if there is somebody willing to take the tamper idea forward I'm happy to try help out but probably can't commit many hours of my time.
Comment #8
megachriz@dman, @ericgsmith
I appreciate sharing your thoughts on this subject. Not sure if understood everything of it exactly, but I'll try to respond it by my best knowledge.
Tamper with fields via event subscribers
There is already a parse event, which I had in my mind of using for Feeds Tamper. If you add a listener to this event with a lower priority than Feeds does, you'll get the parsed result which you then can modify:
I don't think that we need another event layer in this process. I do notice that there is a difference with MigratePreRowSaveEvent: in there, there's an event per row, while in the above example there is one event for all rows (or at least the rows that have been parsed which can happen in chunks, for CSV say 50 records per cycle). I'm not sure if it is bad to have an event for multiple rows instead of an event per row.
I'm not sure if I quite understand this. What I can tell is that Feeds already responds to its own events for performing its core tasks (fetching, parsing, processing). It sounds like you are proposing that each Tamper plugin should respond to an event. I had in mind the use of a FeedsTamperPluginManager which - based on the FeedsType - checks which Tamper plugins are configured for that type. Each configured Tamper plugin will have a weight in Feeds Tamper, which the plugin manager uses to sort the plugins so they run in the right order. On the parse event, the plugin manager would then loop through all the rows and apply all configured Tamper plugins on each row.
Typed Data as internal row format
I haven't quite got into Rules for D8 yet, but it sounds like a good idea to have Rules events for each Feeds event and that you can work with the data within Rules. When responding to the parse event in Rules, Rules would see how each item is expected to look like.
This feature does seem like a nice to have at the moment though, so I think that we should schedule it for after the first alpha release of Feeds.
Decoupled Tamper module
@ericgsmith, Great for working out a 'playground' of the Tamper module. It looks already way more advanced than my initial playground. While a separate Tamper module could add additional time to develop and probably adds extra complexity (because more modules will be in play), I think we should give it a go, certainly because ericgsmith's playground looks like to head in a good direction. If, after a while, it doesn't seem to work out, we can then still go for a more straightforward port of Feeds Tamper.
I propose to check back after a few weeks to see if the Tamper module evolves further and if Feeds Tamper can make use of the Tamper plugins. Let's aim to have steps 1 until 3 from #2917926: Port Feeds Tamper to D8 be done by December 31, 2017. That is:
Would that fit into your schedule, @ericgsmith? If so, I'll plan a few hours a week to work on the code for this as well.
Perhaps we should move the discussion about Tamper over to #2917926: Port Feeds Tamper to D8 as I had there a separate discussion about it with @larowlan.
Comment #9
damienmckennaIt might be a silly question, but is the tamper stuff even needed for the first alpha if there's an underlying API to work from?
Comment #10
megachriz@DamienMcKenna
Thanks for asking!
Strictly spoken, the Tamper module isn't needed for the first alpha as there are possible workarounds. In my opinion though these workarounds are not obvious and therefore hard to apply for non-developers.
My idea of the first alpha release is to have a Feeds version that covers at least basic usage without custom coding. In my opinion at least the Tamper plugin "explode" (with which you can turn a value into multiple values) belongs to the basic use cases. It is often needed when importing CSV files where you can put a list of values into a single column.
Comment #11
megachrizI've updated the links to issues in the issue summary. For the UI of Feeds Tamper an issue has been created #2937728: Add an UI. Development on the Tamper module can be tracked on #2921727: Full release of Tamper, though #2917926: Port Feeds Tamper to D8 currently contains most of the discussion on the module.
Comment #12
megachrizAn UI for the CSV parser is added!
Two followup issues have been created:
#2938505: Add UI for editing and removing custom (CSV) sources
#2938500: Add UI tests for the CSV parser
Both should be aimed for, but they are not blockers for 8.x-3.0-alpha1.
Comment #13
megachrizAdded #2857692: Update existing nodes fails when not mapping to "Feeds Item: Item URL": This value should be of the correct primitive type. as a target for the first alpha release.
Comment #14
megachrizThis week in Feeds D8:
Next Feeds meeting will be on Thursday, February 15 at 19:00 UTC on Drupal Slack in the #feeds channel!
Comment #15
megachrizThis week in Feeds D8:
The plan for the coming week:
Comment #16
megachrizAdded references for follow-ups for the Feeds Tamper UI in the issue summary: #2953361: Allow Tamper plugins to be reordered and #2953362: Allow Tamper plugins to be enabled/disabled.
Comment #17
megachrizThis week in Feeds D8:
The plan for the coming week:
Comment #18
megachrizThis week in Feeds:
The plan for the coming week:
The next Feeds meetup will be on Thursday, March 29 at 18:00 UTC. That's one hour earlier as before. The time shift happens because of daylight saving time in Europe. So in Europe time, it will be at the same time.
Comment #19
cmcintosh commented@MegaCriz I have a bit of an immediate need for feeds. But from the UI designs it looks like feeds is sticking with supporting Node / Users, is this correct?
Comment #20
megachriz@cmcintosh
Other content entity types can be supported as well. I have been experimenting with a wider support of content entity types in my sandbox module Feeds DEV. So far, that particular feature - a generic entity processor - seems to work very well. I have only tested it on Commerce products and Commerce product variations though.
Comment #21
megachrizFeeds 8.x-3.0-alpha1 has been released! Feeds extensible parsers 8.x-1.0-alpha1 has been released as well.
I'll update this issue when an initial plan for the next release is made.
Comment #22
hongpong commentedThanks for all your hard work on this!! It's much appreciated, feeds is such a good module.
Comment #23
mxwright commentedYes! Just tested and it worked for me.
Comment #25
megachriz8.x-3.0-alpha2 has been released!
https://www.drupal.org/project/feeds/releases/8.x-3.0-alpha2
See what is planned for the next release: #2978642: Plan for 8.x-3.0-alpha3 release.