File Structure

The theme is expected to be found in Magento’s directory for themes: app/design/frontend/<VENDOR>/<NAME>. In docker, by default, the theme is located in app/design/frontend/Scandiweb/pwa.

Note:

do not worry that you see no source files (.js, .scss) in your theme. This is expected. You are meant to create files in the same folder with the same name in order to modify them. See extension guide for that.

The source theme (composer installed) is located in vendor/scandipwa/source. Reference it for efficient development. But do not modify the vendor files! Use the extension mechanism for that.

Watch an explanation video

Because the ScandiPWA is compiled to a valid Magento 2 theme, it must follow Magento theme structure.

Note:

initially Magento_Theme folder is empty. You have to compile the application - see the FAQ.

Copy
πŸ“¦base-theme
 ┣ πŸ“‚Magento_Theme # compiled assets
 ┃ ┣ πŸ“‚templates
 ┃ ┃ β”— πŸ“œroot.phtml # root template compiled from "index.development.html" or "index.production.phtml"
 ┃ β”— πŸ“‚web
 ┃   ┣ πŸ“‚assets # compiled from "src/public/assets"
 ┃   β”— πŸ“œ*.(js|css) # compiled JS and CSS
 ┣ πŸ“‚etc # configuration
 ┃ ┣ πŸ“œmodule.xml
 ┃ β”— πŸ“œview.xml
 ┣ πŸ“‚media # theme preview picture in admin panel
 ┃ β”— πŸ“œpreview.png
 ┣ πŸ“œregistration.php # registration file
 β”— πŸ“œtheme.xml # registration file

Browse theme internals

The modern application stack fluidly merged with the flat structure. Notice, the main folders are:

  • component - React components
  • route - application route collection
  • style - application-wise styles
  • query - queries for GraphQL requests
  • type - common React propTypes declarations
  • store - Redux store configuration
  • util - application wise helpers

There are a lot of index.js file in the theme. Do not be afraid of them. Except few exceptions, they are just simple aliases to one of the files in the directory. Exceptions are:

  • app/route/index.js - main router initialization
  • app/store/index.js - reducer combination, Redux initialization
  • app/index.js - application entry-point

Now, observe complete theme source-files related structure:

Copy
πŸ“¦base-theme
 ┣ πŸ“‚node_modules # installed project dependencies (please add to `.gitignore`)
 ┣ πŸ“‚i18n
 ┃ β”— πŸ“œ<LANGUAGE>_<VARIATION>.json
 ┣ πŸ“‚src
 ┃ ┣ πŸ“‚app
 ┃ ┃ ┣ πŸ“‚component
 ┃ ┃ ┃ β”— πŸ“‚<COMPONENT_NAME>
 ┃ ┃ ┃   ┣ πŸ“œ<COMPONENT_NAME>.component.js # template related logic
 ┃ ┃ ┃   ┣ πŸ“œ<COMPONENT_NAME>.container.js # business logic & Redux connection
 ┃ ┃ ┃   ┣ πŸ“œ<COMPONENT_NAME>.style.scss # styles
 ┃ ┃ ┃   ┣ πŸ“œ<COMPONENT_NAME>.config.js # configuration
 ┃ ┃ ┃   ┣ πŸ“œ<COMPONENT_NAME>.test.js # unit tests
 ┃ ┃ ┃   β”— πŸ“œindex.js
 ┃ ┃ ┣ πŸ“‚query
 ┃ ┃ ┃ ┣ πŸ“œ<QUERY_NAME>.query.js
 ┃ ┃ ┃ β”— πŸ“œindex.js
 ┃ ┃ ┣ πŸ“‚route
 ┃ ┃ ┃ ┣ πŸ“‚<ROUTE_NAME>
 ┃ ┃ ┃ ┃ ┣ πŸ“œ<ROUTE_NAME>.component.js
 ┃ ┃ ┃ ┃ ┣ πŸ“œ<ROUTE_NAME>.container.js
 ┃ ┃ ┃ ┃ ┣ πŸ“œ<ROUTE_NAME>.style.scss
 ┃ ┃ ┃ ┃ β”— πŸ“œindex.js
 ┃ ┃ ┃ β”— πŸ“œindex.js
 ┃ ┃ ┣ πŸ“‚store
 ┃ ┃ ┃ ┣ πŸ“‚<STORE_NAME>
 ┃ ┃ ┃ ┃ ┣ πŸ“œ<STORE_NAME>.action.js # action declaration
 ┃ ┃ ┃ ┃ ┣ πŸ“œ<STORE_NAME>.dispatcher.js # action dispatcher (for async executions)
 ┃ ┃ ┃ ┃ ┣ πŸ“œ<STORE_NAME>.reducer.js # action handler
 ┃ ┃ ┃ ┃ β”— πŸ“œindex.js
 ┃ ┃ ┃ β”— πŸ“œindex.js
 ┃ ┃ ┣ πŸ“‚style
 ┃ ┃ ┃ ┣ πŸ“‚abstract # virtual SASS functions, mixins (non compilable). Are injected into every component style!
 ┃ ┃ ┃ ┃ ┣ πŸ“œ_abstract.scss # imports of all abstract functions in right order
 ┃ ┃ ┃ ┃ β”— πŸ“œ_<ABSTRACT_STYLE_PART>.scss
 ┃ ┃ ┃ ┣ πŸ“‚base
 ┃ ┃ ┃ ┃ ┣ πŸ“œ_<HTML_ELEMENT_NAME>.scss
 ┃ ┃ ┃ ┃ ┣ πŸ“œ_reset.scss # CSS reset
 ┃ ┃ ┃ ┃ β”— πŸ“œ_root.scss # ":root" styles (CSS custom variables declaration)
 ┃ ┃ ┃ ┣ πŸ“‚cms
 ┃ ┃ ┃ ┃ ┣ πŸ“‚block
 ┃ ┃ ┃ ┃ ┃ β”— πŸ“œ<CMS_BLOCK_NAME>.scss
 ┃ ┃ ┃ ┃ ┣ πŸ“‚slider
 ┃ ┃ ┃ ┃ ┃ β”— πŸ“œ<SLIDER_NAME>.scss
 ┃ ┃ ┃ ┃ β”— πŸ“œblock.scss
 ┃ ┃ ┃ β”— πŸ“œmain.scss
 ┃ ┃ ┣ πŸ“‚type
 ┃ ┃ ┃ β”— πŸ“œ<PROP_TYPE_GROUP>.js
 ┃ ┃ ┣ πŸ“‚util
 ┃ ┃ ┃ β”— πŸ“‚<UTILITY_GROUP_NAME>
 ┃ ┃ ┃ ┃ ┣ πŸ“œ<UTILITY_NAME>.js
 ┃ ┃ ┃ ┃ β”— πŸ“œindex.js
 ┃ ┃ β”— πŸ“œindex.js
 ┣ πŸ“œpackage-lock.json
 β”— πŸ“œpackage.json

Configuration & build files

TODO:

add notes about webpack configuration naming, explain babel configuration

Copy
πŸ“¦base-theme
 ┣ πŸ“‚config
 ┃ ┣ πŸ“‚FallbackPlugin
 ┃ ┣ πŸ“‚I18nPlugin
 ┃ ┣ πŸ“‚TranslationFunction
 ┃ ┣ πŸ“œbabel.config.js
 ┃ ┣ πŸ“œmeta.config.js
 ┃ ┣ πŸ“œtests.config.js
 ┃ ┣ πŸ“œwebmanifest.config.js
 ┃ ┣ πŸ“œwebpack.core.config.js
 ┃ ┣ πŸ“œwebpack.development.config.js
 ┃ ┣ πŸ“œwebpack.extract-translations.config.js
 ┃ ┣ πŸ“œwebpack.production.config.js
 ┃ β”— πŸ“œwebpack.sw.config.js
 ┣ πŸ“œjsconfig.json
 ┣ πŸ“œprocess-core.yml
 ┣ πŸ“œprocess.yml
 ┣ πŸ“œ.eslintrc
 ┣ πŸ“œ.stylelintrc
 β”— πŸ“œ.graphqlconfig