• Stars
    star
    254
  • Rank 160,264 (Top 4 %)
  • Language
    JavaScript
  • License
    GNU General Publi...
  • Created over 6 years ago
  • Updated about 2 months ago

Reviews

There are no reviews yet. Be the first to send feedback to the community and the maintainers!

Repository Details

Mobile version of Gutenberg - native iOS and Android

Mobile Gutenberg

This is the mobile version of Gutenberg, targeting Android and iOS. It's a React Native library bootstrapped by CRNA and now ejected.

Getting Started

Prerequisites

For a developer experience closer to the one the project maintainers currently have, make sure you have the following tools installed:

  • git
  • nvm
  • Node.js and npm (use nvm to install them)
  • Android Studio to be able to compile the Android version of the app
  • Xcode to be able to compile the iOS app
  • CocoaPods (sudo gem install cocoapods) needed to fetch React and third-party dependencies.
  • Carthage for Appium to be able run iOS UI tests

Depending on your setup, there may be a few configurations needed in Android Studio and Xcode. Please refer to React Native's documentation for the latest requirements for each development environment.

Note that the OS platform used by the maintainers is macOS but the tools and setup should be usable in other platforms too.

Clone the project

  • Clone the project and submodules:
git clone --recurse-submodules https://github.com/wordpress-mobile/gutenberg-mobile.git
  • Or if you already have the project cloned, initialize and update the submodules:
git submodule init
git submodule update

Set up

Before running the demo app, you need to download and install the project dependencies. This is done via the following command:

nvm install
npm install

Run

npm run start:reset

Runs the packager (Metro) in development mode. The packager stays running to serve the app bundle to the clients that request it.

With the packager running, open another terminal window and use the following command to compile and run the Android app:

npm run core android

The app should now open in a connected device or a running emulator and fetch the JavaScript code from the running packager.

To compile and run the iOS variant of the app using the default simulator device, use:

npm run core ios

which will attempt to open your app in the iOS Simulator if you're on a Mac and have it installed.

Running on Other iOS Device Simulators

To compile and run the app using a different device simulator, use:

npm run core ios --simulator="DEVICE_NAME"

For example, if you'd like to run in an iPhone Xs Max, try:

npm run core ios --simulator="iPhone Xs Max"

To see a list of all of your available iOS devices, use xcrun simctl list devices.

Troubleshooting

If the Android emulator doesn't start correctly, or compiling fails with Could not initialize class org.codehaus.groovy.runtime.InvokerHelper or similar, it may help to double check the set up of your development environment against the latest requirements in React Native's documentation. With Android Studio, for example, you will need to configure the ANDROID_HOME environment variable and ensure that your version of JDK matches the latest requirements.

Some times, and especially when tweaking anything in the package.json, Babel configuration (.babelrc) or the Jest configuration (jest.config.js), your changes might seem to not take effect as expected. On those times, you might need to clean various caches before starting the packager. To do that, run the script: npm run start:reset. Other times, you might want to reinstall the NPM packages from scratch and the npm run clean:install script can be handy.

Developing with Visual Studio Code

Although you're not required to use Visual Studio Code for developing gutenberg-mobile, it is the recommended IDE and we have some configuration for it.

When you first open the project in Visual Studio, you will be prompted to install some recommended extensions. This will help with some things like type checking and debugging.

Prompt to install recommended extensions

One of the extensions we are using is the React Native Tools. This allows you to run the packager from VSCode or launch the application on iOS or Android. It also adds some debug configurations so you can set breakpoints and debug the application directly from VSCode. Take a look at the extension documentation for more details.

Unit Tests

Use the following command to run the test suite:

npm run test

It will run the jest test runner on your tests. The tests are running on the desktop against Node.js.

To run the tests with debugger support, start it with the following CLI command:

npm run test:debug

Then, open chrome://inspect in Chrome to attach the debugger (look into the "Remote Target" section). While testing/developing, feel free to sprinkle debugger statements anywhere in the code that you'd like the debugger to break.

Writing and Running Unit Tests

This project is set up to use jest for tests. You can configure whatever testing strategy you like, but jest works out of the box. Create test files in directories called __tests__ or with the .test.js extension to have the files loaded by jest. See an example test here. The jest documentation is also a wonderful resource, as is the React Native testing tutorial.

UI Tests

This repository uses Appium to run UI tests. The tests live in __device-tests__ and are written using Appium to run tests against simulators and real devices. To run these you'll need to check off a few things:

  • When running the tests, you'll need to ensure the Metro bundler (npm run start) is not running.
  • Appium CLI installed and available globally. We also recommend using appium-doctor to ensure all of Appium's dependencies are good to go. You don't have to worry about starting the server yourself, the tests handle starting the server on port 4723, just be sure that the port is free or feel free to change the port number in the test file.
  • For iOS a simulator should automatically launch but for Android you'll need to have an emulator with at least platform version 8.0 fired up and running.

Then, to run the UI tests on iOS:

npm run test:e2e:ios:local

and for Android:

npm run test:e2e:android:local

Note: Make sure you've run the above commands at least once, so the demo app binaries are built before running individual tests below.

To run a single test instead of the entire suite, use npm run device-tests:local. Here's an example that runs only gutenberg-editor-paragraph.test:

TEST_RN_PLATFORM=ios npm run device-tests:local gutenberg-editor-paragraph.test

Note: You might experience problems that seem to be related to the tests starting the Appium server, e.g. errors that say Connection Refused, Connection Reset or The requested environment is not available. For now, you can manually start the Appium server via Appium Inspector or the CLI, then change the port number in the tests while (optionally) commenting out related code in the beforeAll and afterAll block.

For a more detailed outline of the UI tests and how to get started writing one, please visit the UI Test documentation and our contributing guide.

Static analysis and code style

The project includes a linter (eslint) to perform codestyle and static analysis of the code. The configuration used is the same as the one in the Gutenberg project. To perform the check, run:

npm run lint

To have the linter also fix the violations run: npm run lint:fix.

You might want to use Visual Studio Code as an editor. The project includes the configuration needed to use the above codestyle and linting tools automatically.

Internationalization (i18n)

The support for i18n in the project is provided by three main areas for the different plugins included in Gutenberg Mobile:

  1. Translations files download
  2. Locale setup
  3. Localization strings file generation

Main areas

Translation files download

A translation file is basically a JSON object that contains key-value items with the translation for each individual string. This content is fetched from translate.wordpress.org that holds translations for WordPress and a list of different plugins like Gutenberg.

These files are cached under the folder located at src/i18n-cache/<PLUGIN_NAME>, and can be optimized depending on the command used for fetching them. Additionally, an index file (index.js) is generated that acts as the entry point to import and get translations for each plugin.

Fetched translations contain all the strings of the plugin, including strings that are not used in the native version of the editor, however, and in order to reduce their file size, they can be optimized by filtering out the unused strings.

By default, when installing dependencies, un-optimized translations will be downloaded for the plugins specified in the i18n:check-cache NPM command within the package.json file. The reason for getting the un-optimized version is purely for speed reasons, as the optimization process takes up several minutes.

For the optimized versions, similarly, we have the i18n:update NPM command that can be used for this purpose. This command is also automatically run when generating the bundle via npm run bundle, this way we guarantee that a new version of the bundle contains up-to-date translations. On the other hand, it's important to mention that this command also generates the localization strings files described in a later section.

Locale setup

This is done upon the editor initialization, an array containing the following items related to each plugin is passed:

[
  {
    domain: <DOMAIN / PLUGIN NAME>, (i.e. `jetpack`)
    getTranslation: <CALLBACK_FOR_GETTING_TRANSLATION> (i.e. `getTranslation` function imported from `src/i18n-cache/jetpack/index.js`)
  },
  ...
]

Localization strings file generation

Some of the strings referenced in the editor are only used in the native version, these strings are not included in the translations fetched from translate.wordpress.org, however, they are part of the WordPress app translations. For this reason, we generate the following localization strings files, which contain these types of string, for each platform, and that are bundled and incorporated in the translation pipeline of the app.

These files are generated via the i18n:update NPM command, and like translations, they are also produced when generating the bundle.

NPM commands

  • npm run i18n:update: Downloads optimized translations and generate localization strings files for all plugins. NOTE: This command is attached to bundle NPM command via prebundle:js, so it will be automatically executed when generating a bundle.
  • npm run i18n:check-cache: Downloads un-optimized translations for plugins that don't have a cache folder. NOTE: This command is attached to dependency installation via postinstall, so it will be automatically executed when installing dependencies.

How to add a new plugin

  1. Identify the i18n domain, which usually matches the plugin's name (i.e. jetpack).
  2. Identify the GlotPress project slug (i.e. wp-plugins/jetpack for URL https://translate.wordpress.org/projects/wp-plugins/jetpack/)
  3. Identify the path to the plugin's source code (i.e. ./jetpack/projects/plugins/jetpack/extensions).
  4. Append the plugin's name, GlotPress project slug, and plugin's source code to the arguments of i18n:update and i18n:update:test NPM commands.
  5. Append the plugin's name and GlotPress project slug to the arguments of i18n:check-cache NPM command.

Example:

"scripts": {
  ...
  "i18n:check-cache": "... jetpack wp-plugins/jetpack",
  "i18n:update": "... jetpack wp-plugins/jetpack ./jetpack/projects/plugins/jetpack/extensions",
  "i18n:update:test": "... jetpack wp-plugins/jetpack ./jetpack/projects/plugins/jetpack/extensions",
  ...
}
  1. Add the i18n domain of the plugin and the callback for getting translation to the editor initialization. Example:
import { getTranslation as getJetpackTranslation } from './i18n-translations/jetpack';
...

const pluginTranslations = [
	{
		domain: 'jetpack',
		getTranslation: getJetpackTranslation,
	},
	...
];
  1. (Optional) In some cases, it's needed to build the source code in order to extract the used strings. Consider adding a command in bin/i18n-update.sh file for this purpose (e.g. ./bin/run-jetpack-command.sh "-C projects/packages/videopress build" to build VideoPress package)

Caveats

  • Strings that are only used in the native version, and reference a context, won't be included in the localization strings files hence, they won't be translated. This is a limitation in the format of the localization strings files.
  • Localization strings files don’t support domains, so the strings extracted from plugins that are only used in the native version, will be unified in the same file, which might involve string conflicts.

Troubleshooting

A string is missing the translation

This can be produced by several causes, check the following steps in order to identify the source:

  • Verify that the string uses the __ i18n function or similar (reference).
  • Check for warnings in the output when running i18n:update NPM command, especially the following ones:
    • Parsing files issues (i.e. Debug (make-pot): Could not parse file <FILE>)
    • Missing strings in translation files (i.e. WARNING: The following strings are missing from translations:)
  • If the string is only used in the native version, the translation won't be available until the a new version of the app is cut and its translations are requested. Check if the string is included in the localization strings files, if not, verify the output of i18n:update NPM command and look for warnings that reference the string.

License

Gutenberg Mobile is an Open Source project covered by the GNU General Public License version 2.

More Repositories

1

WordPress-iOS

WordPress for iOS - Official repository
Swift
3,686
star
2

WordPress-Android

WordPress for Android
Kotlin
2,971
star
3

WordPress-Editor-iOS

⛔️ [DEPRECATED] A reusable iOS rich text editor component.
JavaScript
1,061
star
4

AztecEditor-Android

A reusable native Android rich text editor component.
Kotlin
698
star
5

AztecEditor-iOS

A reusable native iOS visual HTML text editor component.
Swift
615
star
6

PasscodeLock-Android

Android Library that provides passcode lock to your app
Java
353
star
7

WordPress-Editor-Android

⛔️ [DEPRECATED] A reusable Android rich text editor component.
Java
188
star
8

MediaPicker-iOS

WPMediaPicker is an iOS controller that allows capture and picking of media assets.
Objective-C
110
star
9

wpxmlrpc

A lightweight XML-RPC encoder/decoder for iOS, OS X, and tvOS
Objective-C
88
star
10

WordPress-API-iOS

A library to connect to WordPress sites using XML-RPC or the WordPress.com REST API
Objective-C
66
star
11

WordPress-FluxC-Android

WordPress Network and Persistence layer based on the Flux architecture
Kotlin
57
star
12

MediaEditor-iOS

Easy add image editing features to your iOS app! 🖼️
Swift
49
star
13

EmailChecker

Email checking library for Android and iOS
C++
46
star
14

WordPressKit-iOS

WordPressKit offers a clean and simple WordPress.com and WordPress.org network API.
Swift
42
star
15

swift-style-guide

Swift Style Guide
35
star
16

WordPress-Utils-Android

Common utilities used by WordPress-Android.
Java
33
star
17

release-toolkit

Shared tools used in release automation
Ruby
31
star
18

react-native-aztec

Wrapping Aztec Android and Aztec iOS in a React Native component
Java
29
star
19

cocoapods-repo-update

A CocoaPods plugin that updates your specs repos on pod install if needed.
Ruby
28
star
20

WordCamp-Android

WordCamp for Android
Java
24
star
21

WordPress-WindowsPhone

WordPress for WindowsPhone
C#
20
star
22

NSObject-SafeExpectations

No more crashes getting unexpected values from a NSDictionary
Objective-C
19
star
23

MediaPicker-Android

MediaPicker is an Android Fragment that allows capture and selection of media assets from a variety of sources.
Java
19
star
24

WordPress-iOS-Shared

Shared components used in building the WordPress iOS apps and other library components
Objective-C
18
star
25

WordPressAuthenticator-iOS

Swift
17
star
26

NSURL-IDN

Support for IDN (punycode) in NSURL
Objective-C
14
star
27

WordPress-Login-Flow-Android

Pluggable WordPress login flow for Android
Java
14
star
28

objective-c-style-guide

Objective-C Style Guide
12
star
29

test-cases

Test case repository for Gutenberg editor used in the WordPress mobile app
11
star
30

WordPressCom-Stats-iOS

⛔️ [DEPRECATED] Reusable component for displaying WordPress.com site stats in an iOS application
Objective-C
10
star
31

WordPressFlux-iOS

WordPressFlux
Swift
8
star
32

WordPressCom-Analytics-iOS

⛔️ [DEPRECATED] Library for handling Analytics tracking in WPiOS
Objective-C
8
star
33

WordPress-Networking-Android

Networking library used by WordPress-Android and other WordPress-*-Android components
Java
7
star
34

PersistentEditText-Android

Android EditText subclass with persistence
Java
7
star
35

WordPressUI-iOS

Swift
7
star
36

WordPress-BlackBerry-Legacy

WordPress for BlackBerry OS 7.1 and earlier.
Java
5
star
37

release-toolkit-gutenberg-mobile

Automation Scripts for Releasing Gutenberg-Mobile Updates to the WordPress Mobile Apps.
Go
5
star
38

circleci-orbs

The source code for some CircleCI orbs published by wordpress-mobile
Shell
5
star
39

GutenbergKit

Swift
5
star
40

WordPress-Analytics-Android

⛔️ [DEPRECATED] Library for handling Analytics tracking in WordPress Android.
Java
4
star
41

cocoapods-specs

Our internal CocoaPods spec repository for Automattic's internal pods
Ruby
4
star
42

WordPress-BlackBerry

WordPress for BlackBerry 10
C++
4
star
43

EmailChecker-Android

Email checking library for Android
Kotlin
3
star
44

WordCamp-iOS

WordCamp for iOS
3
star
45

WordPress-Editor-Common

Common code of Android and iOS rich text editor component.
JavaScript
3
star
46

WordPress-Android-Libraries-Gradle-Plugin

Gradle Plugin for WordPress Android library development setup
Groovy
3
star
47

test-case-reminder-bot

GitHub bot that drops a comment to the PR about what to test when a specific file changes in gutenberg repo. Test cases and configurations live in gutenberg-tests repo.
Ruby
3
star
48

WordPress-MediaPicker-Android

Kotlin
2
star
49

editor-test-ios

Objective-C
2
star
50

docker-glotpress-linter

A docker image that lints files before they're uploaded to GlotPress
PHP
2
star
51

WordPress-Ratings-iOS

Library for handling App Ratings Logic
Objective-C
2
star
52

WordPressMocks

Network mocking for testing the WordPress mobile apps
Java
2
star
53

app-secrets-management-ios

Files related to iOS application secrets management.
Shell
2
star
54

react-native-libraries-publisher

Shell
1
star
55

WordPress-Lint-Android

Pluggable lint module for WordPress-Android
Kotlin
1
star
56

automatization-scripts

Shell
1
star
57

docker-gb-mobile-image

Dockerfile
1
star
58

gutenberg-plugin-hello-world

JavaScript
1
star
59

WordPress-HealthCheck-iOS

Health check for common iOS problems
Shell
1
star
60

app-blocking-plugins

This repository contains a list of plugins that cause problems with WordPress Apps connecting correctly.
1
star
61

Pioupiou

Micro blogging app using your WordPress site as backend.
Java
1
star
62

WordPress-HealthCheck-Common

Health-Check cross-platform test cases
HTML
1
star