Przeglądaj źródła

Merge pull request #9549 from weseek/master

Release v7.1.8
mergify[bot] 1 rok temu
rodzic
commit
35786a7889

+ 1 - 1
.github/workflows/reusable-app-prod.yml

@@ -181,7 +181,7 @@ jobs:
     container:
     container:
       # Match the Playwright version
       # Match the Playwright version
       # https://github.com/microsoft/playwright/issues/20010
       # https://github.com/microsoft/playwright/issues/20010
-      image: mcr.microsoft.com/playwright:v1.46.0-jammy
+      image: mcr.microsoft.com/playwright:v1.49.1-jammy
 
 
     strategy:
     strategy:
       fail-fast: false
       fail-fast: false

+ 1 - 1
apps/app/package.json

@@ -1,6 +1,6 @@
 {
 {
   "name": "@growi/app",
   "name": "@growi/app",
-  "version": "7.1.7",
+  "version": "7.1.8-RC.0",
   "license": "MIT",
   "license": "MIT",
   "private": "true",
   "private": "true",
   "scripts": {
   "scripts": {

+ 43 - 37
apps/app/playwright/20-basic-features/comments.spec.ts

@@ -1,49 +1,55 @@
 import { test, expect } from '@playwright/test';
 import { test, expect } from '@playwright/test';
 
 
-test('Create comment page', async({ page }) => {
-  await page.goto('/comment');
-  await page.getByTestId('editor-button').click();
-  await page.getByTestId('save-page-btn').click();
-  await expect(page.locator('.page-meta')).toBeVisible();
-});
+test.describe('Comment', () => {
 
 
-test('Successfully add comments', async({ page }) => {
-  const commentText = 'add comment';
-  await page.goto('/comment');
+  // make tests run in serial
+  test.describe.configure({ mode: 'serial' });
 
 
-  // Add comment
-  await page.getByTestId('page-comment-button').click();
-  await page.getByTestId('open-comment-editor-button').click();
-  await page.locator('.cm-content').fill(commentText);
-  await page.getByTestId('comment-submit-button').first().click();
+  test('Create comment page', async({ page }) => {
+    await page.goto('/comment');
+    await page.getByTestId('editor-button').click();
+    await page.getByTestId('save-page-btn').click();
+    await expect(page.locator('.page-meta')).toBeVisible();
+  });
 
 
-  await expect(page.locator('.page-comment-body')).toHaveText(commentText);
-  await expect(page.getByTestId('page-comment-button').locator('.grw-count-badge')).toHaveText('1');
-});
+  test('Successfully add comments', async({ page }) => {
+    const commentText = 'add comment';
+    await page.goto('/comment');
 
 
-test('Successfully reply comments', async({ page }) => {
-  const commentText = 'reply comment';
-  await page.goto('/comment');
+    // Add comment
+    await page.getByTestId('page-comment-button').click();
+    await page.getByTestId('open-comment-editor-button').click();
+    await page.locator('.cm-content').fill(commentText);
+    await page.getByTestId('comment-submit-button').first().click();
 
 
-  // Reply comment
-  await page.getByTestId('page-comment-button').click();
-  await page.getByTestId('comment-reply-button').click();
-  await page.locator('.cm-content').fill(commentText);
-  await page.getByTestId('comment-submit-button').first().click();
+    await expect(page.locator('.page-comment-body')).toHaveText(commentText);
+    await expect(page.getByTestId('page-comment-button').locator('.grw-count-badge')).toHaveText('1');
+  });
 
 
-  await expect(page.locator('.page-comment-body').nth(1)).toHaveText(commentText);
-  await expect(page.getByTestId('page-comment-button').locator('.grw-count-badge')).toHaveText('2');
-});
+  test('Successfully reply comments', async({ page }) => {
+    const commentText = 'reply comment';
+    await page.goto('/comment');
+
+    // Reply comment
+    await page.getByTestId('comment-reply-button').click();
+    await page.locator('.cm-content').fill(commentText);
+    await page.getByTestId('comment-submit-button').first().click();
 
 
-// test('Successfully delete comments', async({ page }) => {
-//   await page.goto('/comment');
+    await expect(page.locator('.page-comment-body').nth(1)).toHaveText(commentText);
+    await expect(page.getByTestId('page-comment-button').locator('.grw-count-badge')).toHaveText('2');
+  });
 
 
-//   await page.getByTestId('page-comment-button').click();
-//   await page.getByTestId('comment-delete-button').first().click({ force: true });
-//   await expect(page.getByTestId('page-comment-delete-modal')).toBeVisible();
-//   await page.getByTestId('delete-comment-button').click();
+  // test('Successfully delete comments', async({ page }) => {
+  //   await page.goto('/comment');
 
 
-//   await expect(page.getByTestId('page-comment-button').locator('.grw-count-badge')).toHaveText('0');
-// });
+  //   await page.getByTestId('page-comment-button').click();
+  //   await page.getByTestId('comment-delete-button').first().click({ force: true });
+  //   await expect(page.getByTestId('page-comment-delete-modal')).toBeVisible();
+  //   await page.getByTestId('delete-comment-button').click();
 
 
-// TODO: https://redmine.weseek.co.jp/issues/139520
+  //   await expect(page.getByTestId('page-comment-button').locator('.grw-count-badge')).toHaveText('0');
+  // });
+
+  // TODO: https://redmine.weseek.co.jp/issues/139520
+
+});

+ 1 - 1
apps/app/src/server/service/page/index.ts

@@ -4391,7 +4391,7 @@ class PageService implements IPageService {
     const Page = mongoose.model('Page') as unknown as PageModel;
     const Page = mongoose.model('Page') as unknown as PageModel;
 
 
     const ancestorPaths = isTopPage(path) ? ['/'] : collectAncestorPaths(path); // root path is necessary for rendering
     const ancestorPaths = isTopPage(path) ? ['/'] : collectAncestorPaths(path); // root path is necessary for rendering
-    const regexps = ancestorPaths.map(path => new RegExp(generateChildrenRegExp(path))); // cannot use re2
+    const regexps = ancestorPaths.map(path => generateChildrenRegExp(path)); // cannot use re2
 
 
     // get pages at once
     // get pages at once
     const queryBuilder = new PageQueryBuilder(Page.find({ path: { $in: regexps } }), true);
     const queryBuilder = new PageQueryBuilder(Page.find({ path: { $in: regexps } }), true);

+ 1 - 1
apps/slackbot-proxy/package.json

@@ -1,6 +1,6 @@
 {
 {
   "name": "@growi/slackbot-proxy",
   "name": "@growi/slackbot-proxy",
-  "version": "7.1.7-slackbot-proxy.0",
+  "version": "7.1.8-slackbot-proxy.0",
   "license": "MIT",
   "license": "MIT",
   "private": "true",
   "private": "true",
   "scripts": {
   "scripts": {

+ 2 - 2
package.json

@@ -1,6 +1,6 @@
 {
 {
   "name": "growi",
   "name": "growi",
-  "version": "7.1.7",
+  "version": "7.1.8-RC.0",
   "description": "Team collaboration software using markdown",
   "description": "Team collaboration software using markdown",
   "license": "MIT",
   "license": "MIT",
   "private": "true",
   "private": "true",
@@ -46,7 +46,7 @@
     "@changesets/changelog-github": "^0.5.0",
     "@changesets/changelog-github": "^0.5.0",
     "@changesets/cli": "^2.27.3",
     "@changesets/cli": "^2.27.3",
     "@faker-js/faker": "^9.0.1",
     "@faker-js/faker": "^9.0.1",
-    "@playwright/test": "^1.46.0",
+    "@playwright/test": "^1.49.1",
     "@swc-node/register": "^1.9.1",
     "@swc-node/register": "^1.9.1",
     "@swc/core": "^1.5.25",
     "@swc/core": "^1.5.25",
     "@swc/helpers": "^0.5.11",
     "@swc/helpers": "^0.5.11",

+ 6 - 0
packages/core/CHANGELOG.md

@@ -1,5 +1,11 @@
 # @growi/core
 # @growi/core
 
 
+## 1.3.1
+
+### Patch Changes
+
+- [#9550](https://github.com/weseek/growi/pull/9550) [`acd3787`](https://github.com/weseek/growi/commit/acd3787fc4b8c8630ba9fa5a06d837639da8d10a) Thanks [@yuki-takei](https://github.com/yuki-takei)! - Fix generateChildrenRegExp method
+
 ## 1.3.0
 ## 1.3.0
 
 
 ### Minor Changes
 ### Minor Changes

+ 1 - 1
packages/core/package.json

@@ -1,6 +1,6 @@
 {
 {
   "name": "@growi/core",
   "name": "@growi/core",
-  "version": "1.3.0",
+  "version": "1.3.1",
   "description": "GROWI Core Libraries",
   "description": "GROWI Core Libraries",
   "license": "MIT",
   "license": "MIT",
   "keywords": [
   "keywords": [

+ 55 - 0
packages/core/src/utils/page-path-utils/generate-children-regexp.spec.ts

@@ -0,0 +1,55 @@
+import { describe, expect, test } from 'vitest';
+
+import { generateChildrenRegExp } from './generate-children-regexp';
+
+describe('generateChildrenRegExp', () => {
+  describe.each([
+    {
+      path: '/',
+      expected: '^\\/[^/]+$',
+      validPaths: ['/child', '/test'],
+      invalidPaths: ['/', '/child/grandchild'],
+    },
+    {
+      path: '/parent',
+      expected: '^\\/parent(\\/[^/]+)\\/?$',
+      validPaths: ['/parent/child', '/parent/test'],
+      invalidPaths: ['/parent', '/parent/child/grandchild', '/other/path'],
+    },
+    {
+      path: '/parent (with brackets)',
+      expected: '^\\/parent \\(with brackets\\)(\\/[^/]+)\\/?$',
+      validPaths: ['/parent (with brackets)/child', '/parent (with brackets)/test'],
+      invalidPaths: ['/parent (with brackets)', '/parent (with brackets)/child/grandchild'],
+    },
+    {
+      path: '/parent[with square]',
+      expected: '^\\/parent\\[with square\\](\\/[^/]+)\\/?$',
+      validPaths: ['/parent[with square]/child', '/parent[with square]/test'],
+      invalidPaths: ['/parent[with square]', '/parent[with square]/child/grandchild'],
+    },
+    {
+      path: '/parent*with+special?chars',
+      expected: '^\\/parent\\*with\\+special\\?chars(\\/[^/]+)\\/?$',
+      validPaths: ['/parent*with+special?chars/child', '/parent*with+special?chars/test'],
+      invalidPaths: ['/parent*with+special?chars', '/parent*with+special?chars/child/grandchild'],
+    },
+  ])('with path: $path', ({
+    path, expected, validPaths, invalidPaths,
+  }) => {
+    test('should generate correct regexp pattern', () => {
+      const result = generateChildrenRegExp(path);
+      expect(result.source).toBe(expected);
+    });
+
+    test.each(validPaths)('should match valid path: %s', (validPath) => {
+      const result = generateChildrenRegExp(path);
+      expect(validPath).toMatch(result);
+    });
+
+    test.each(invalidPaths)('should not match invalid path: %s', (invalidPath) => {
+      const result = generateChildrenRegExp(path);
+      expect(invalidPath).not.toMatch(result);
+    });
+  });
+});

+ 16 - 0
packages/core/src/utils/page-path-utils/generate-children-regexp.ts

@@ -0,0 +1,16 @@
+import escapeStringRegexp from 'escape-string-regexp';
+
+import { isTopPage } from './is-top-page';
+
+/**
+ * Generate RegExp instance for one level lower path
+ */
+export const generateChildrenRegExp = (path: string): RegExp => {
+  // https://regex101.com/r/laJGzj/1
+  // ex. /any_level1
+  if (isTopPage(path)) return new RegExp(/^\/[^/]+$/);
+
+  // https://regex101.com/r/mrDJrx/1
+  // ex. /parent/any_child OR /any_level1
+  return new RegExp(`^${escapeStringRegexp(path)}(\\/[^/]+)\\/?$`);
+};

+ 1 - 13
packages/core/src/utils/page-path-utils/index.ts

@@ -8,6 +8,7 @@ import { addTrailingSlash } from '../path-utils';
 import { isTopPage as _isTopPage } from './is-top-page';
 import { isTopPage as _isTopPage } from './is-top-page';
 
 
 export const isTopPage = _isTopPage;
 export const isTopPage = _isTopPage;
+export * from './generate-children-regexp';
 
 
 /**
 /**
  * Whether path is the top page of users
  * Whether path is the top page of users
@@ -276,19 +277,6 @@ export const hasSlash = (str: string): boolean => {
   return str.includes('/');
   return str.includes('/');
 };
 };
 
 
-/**
- * Generate RegExp instance for one level lower path
- */
-export const generateChildrenRegExp = (path: string): RegExp => {
-  // https://regex101.com/r/laJGzj/1
-  // ex. /any_level1
-  if (isTopPage(path)) return new RegExp(/^\/[^/]+$/);
-
-  // https://regex101.com/r/mrDJrx/1
-  // ex. /parent/any_child OR /any_level1
-  return new RegExp(`^${path}(\\/[^/]+)\\/?$`);
-};
-
 /**
 /**
  * Get username from user page path
  * Get username from user page path
  * @param path string
  * @param path string

+ 1 - 2
packages/ui/package.json

@@ -37,8 +37,7 @@
     "lint:typecheck": "vue-tsc --noEmit",
     "lint:typecheck": "vue-tsc --noEmit",
     "lint": "npm-run-all -p lint:*"
     "lint": "npm-run-all -p lint:*"
   },
   },
-  "dependencies": {
-  },
+  "dependencies": {},
   "devDependencies": {
   "devDependencies": {
     "@growi/core": "workspace:^",
     "@growi/core": "workspace:^",
     "@growi/core-styles": "workspace:^",
     "@growi/core-styles": "workspace:^",

Plik diff jest za duży
+ 145 - 210
pnpm-lock.yaml


Niektóre pliki nie zostały wyświetlone z powodu dużej ilości zmienionych plików