[epiphany/mcatanzaro/web-app-id] progress




commit b0797444cac192f97b8671d3cb02018f08391868
Author: Michael Catanzaro <mcatanzaro redhat com>
Date:   Wed Nov 24 13:24:18 2021 -0600

    progress

 lib/ephy-web-app-utils.c | 106 ++++++++++++++++++++++++++++++++++++++---------
 lib/ephy-web-app-utils.h |   2 +
 src/ephy-shell.c         |   9 ++--
 3 files changed, 93 insertions(+), 24 deletions(-)
---
diff --git a/lib/ephy-web-app-utils.c b/lib/ephy-web-app-utils.c
index d60b7dfa6..1eee39467 100644
--- a/lib/ephy-web-app-utils.c
+++ b/lib/ephy-web-app-utils.c
@@ -33,15 +33,28 @@
 #include <string.h>
 #include <fcntl.h>
 
-/* Web Apps are installed in the default config dir of the user.
- * Every app has its own profile directory. To create a web app
- * an id needs to be generated using the given name as
- * <normalized-name>-checksum.
+/* Web apps are installed in the default data dir of the user. Every
+ * app has its own profile directory. To create a web app, an ID needs
+ * to be generated using the given name as <normalized-name>-checksum.
+ * The ID is used to uniquely identify the app.
  *
- * The id is used to uniquely identify the app.
+ *  - Name: the user-visible pretty app name
+ *  - Normalized name: lowercase name
+ *  - Checksum: SHA-1 of name
+ *  - ID: <normalized-name>-<checksum>
  *  - Program name: org.gnome.Epiphany.WebApp-<id>
+ *  - GApplication ID: see below
  *  - Profile directory: <program-name>
- *  - Desktop file: <profile-dir>/<program-name>.desktop
+ *  - Desktop file: <profile-dir>/<gapplication-id>.desktop
+ *
+ * Note that name and program name are different, as are ID and
+ * GApplication ID. Yes, this is confusing.
+ *
+ * For GApplication ID, there are two cases:
+ *
+ *  - If <id> is safe to use in a D-Bus identifier,
+ *    then: GApplication ID is <program-name>
+ *  - otherwise: GAppliation ID is org.gnome.Epiphany.WebApp-<checksum>
  *
  * System web applications have a profile dir without a desktop file.
  */
@@ -97,17 +110,72 @@ get_app_profile_directory_name (const char *id)
   return encoded;
 }
 
+static const char *
+get_app_id_from_program_name (const char *name)
+{
+  if (!g_str_has_prefix (name, EPHY_WEB_APP_PROGRAM_NAME_PREFIX)) {
+    g_warning ("Program name %s does not begin with required prefix %s", name, 
EPHY_WEB_APP_PROGRAM_NAME_PREFIX);
+    return NULL;
+  }
+
+  return name + strlen (EPHY_WEB_APP_PROGRAM_NAME_PREFIX);
+}
+
 static char *
-get_app_desktop_filename (const char *id)
+get_gapplication_id_from_program_name (const char *name)
 {
-  char *filename;
-  char *encoded;
+  g_auto (GStrv) split = NULL;
+  g_autofree char *id = NULL;
 
-  filename = g_strconcat (EPHY_WEB_APP_PROGRAM_NAME_PREFIX, id, ".desktop", NULL);
-  encoded = get_encoded_path (filename);
-  g_free (filename);
+  /* Ideally we would convert hyphens to underscores here, because
+   * hyphens are not very friendly to D-Bus. However, changing this
+   * would require a new profile migration because the GApplication ID
+   * must exactly match the desktop file basename.
+   */
+  if (g_application_id_is_valid (name))
+    return g_strdup (name);
 
-  return encoded;
+  /* Split name into: org.gnome.Epiphany.WebApp-<normalized-name>-<checksum> */
+  split = g_strsplit (name, "-", -1);
+  if (g_strv_length (split) != 3) {
+    g_warning ("Program name %s is broken: must have three hyphens", name);
+    return NULL;
+  }
+
+  /* We'll simply omit the <normalized-name> from the app ID, in order
+   * to avoid problematic characters. Ideally we would use an underscore
+   * here too, rather than a hyphen, but let's be consistent with
+   * existing web apps.
+   */
+  id = g_strconcat (EPHY_WEB_APP_PROGRAM_NAME_PREFIX, split[2], NULL);
+
+  if (!g_application_id_is_valid (id)) {
+    g_warning ("Program name %s is broken: derived ID %s is not a valid app ID (is the final component 
alphanumeric?)", name, id);
+    return NULL;
+  }
+
+  return g_steal_pointer (&id);
+}
+
+static char *
+get_gapplication_id_from_id (const char *id)
+{
+  g_autofree char *program_name = g_strconcat (EPHY_WEB_APP_PROGRAM_NAME_PREFIX, id, NULL);
+  return get_gapplication_id_from_program_name (program_name);
+}
+
+static char *
+get_app_desktop_filename (const char *id)
+{
+  g_autofree char *gapplication_id = NULL;
+  g_autofree char *filename = NULL;
+
+  /* Warning: the GApplication ID must exactly match the desktop file's
+   * basename. Don't overthink this or stuff will break, e.g. GNotification.
+   */
+  gapplication_id = get_gapplication_id_from_id (id);
+  filename = g_strconcat (gapplication_id, ".desktop", NULL);
+  return filename ? get_encoded_path (filename) : NULL;
 }
 
 const char *
@@ -136,15 +204,13 @@ ephy_web_application_get_program_name_from_profile_directory (const char *profil
   return name;
 }
 
-static const char *
-get_app_id_from_program_name (const char *name)
+char *
+ephy_web_application_get_gapplication_id_from_profile_directory (const char *profile_dir)
 {
-  if (!g_str_has_prefix (name, EPHY_WEB_APP_PROGRAM_NAME_PREFIX)) {
-    g_warning ("Program name %s does not begin with required prefix %s", name, 
EPHY_WEB_APP_PROGRAM_NAME_PREFIX);
-    return NULL;
-  }
+  const char *program_name;
 
-  return name + strlen (EPHY_WEB_APP_PROGRAM_NAME_PREFIX);
+  program_name = ephy_web_application_get_program_name_from_profile_directory (profile_dir);
+  return get_gapplication_id_from_program_name (program_name);
 }
 
 static const char *
diff --git a/lib/ephy-web-app-utils.h b/lib/ephy-web-app-utils.h
index 3d68263e6..5c643636c 100644
--- a/lib/ephy-web-app-utils.h
+++ b/lib/ephy-web-app-utils.h
@@ -47,6 +47,8 @@ char               *ephy_web_application_get_app_id_from_name (const char *name)
 
 const char         *ephy_web_application_get_program_name_from_profile_directory (const char *profile_dir);
 
+char               *ephy_web_application_get_gapplication_id_from_profile_directory (const char 
*profile_dir);
+
 char               *ephy_web_application_create (const char *id, const char *address, const char *name, 
GdkPixbuf *icon, EphyWebApplicationOptions options);
 
 char               *ephy_web_application_ensure_for_app_info (GAppInfo *app_info);
diff --git a/src/ephy-shell.c b/src/ephy-shell.c
index d7d705bcf..7ae354771 100644
--- a/src/ephy-shell.c
+++ b/src/ephy-shell.c
@@ -1284,17 +1284,18 @@ ephy_shell_get_prefs_dialog (EphyShell *shell)
 void
 _ephy_shell_create_instance (EphyEmbedShellMode mode)
 {
-  const char *id = NULL;
+  g_autofree char *id = NULL;
 
   g_assert (ephy_shell == NULL);
 
   if (mode == EPHY_EMBED_SHELL_MODE_APPLICATION) {
     const char *profile_dir = ephy_profile_dir ();
-    const char *web_id = ephy_web_application_get_program_name_from_profile_directory (profile_dir);
 
-    id = web_id;
+    id = ephy_web_application_get_gapplication_id_from_profile_directory (profile_dir);
+    if (id == NULL)
+      g_error ("Cannot start web app instance: %s is not a valid profile directory", profile_dir);
   } else {
-    id = APPLICATION_ID;
+    id = g_strdup (APPLICATION_ID);
   }
 
   ephy_shell = EPHY_SHELL (g_object_new (EPHY_TYPE_SHELL,


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]