Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion docs/apis.md
Original file line number Diff line number Diff line change
Expand Up @@ -250,5 +250,5 @@ The [[Question API]] (which can be divided into the Question bank API and the Qu

- [[Plugins]] - plugin types also have their own APIs
- [[Callbacks]] - list of all callbacks in Moodle
- [[Coding style]] - general information about writing PHP code for Moodle
- [Coding style](/general/development/policies/codingstyle) - general information about writing PHP code for Moodle
- [[Session locks]]
2 changes: 1 addition & 1 deletion docs/guides/moodleapp/coding-style.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ title: Moodle App Coding Style
sidebar_position: 2
---

This document outlines the exceptions to the [[Coding style]] and [[JavaScript Coding Style]] which apply to the Moodle App and also includes rules for other technologies that are used in the app, like Typescript and Angular.
This document outlines the exceptions to the [Coding style](/general/development/policies/codingstyle) and [[JavaScript Coding Style]] which apply to the Moodle App and also includes rules for other technologies that are used in the app, like Typescript and Angular.

Unless otherwise specified, developers should follow the indications included on those documents.

Expand Down
4 changes: 2 additions & 2 deletions general/development/process.md
Original file line number Diff line number Diff line change
Expand Up @@ -199,7 +199,7 @@ Bug fixes, and minor features or enhancements should go through the following pr

### Make sure there is a tracker issue

Every change must have an issue in the tracker. If you are fixing a bug, there is probably one there already, but if not, create one. [[Tracker tips|Tips for searching tracker]].
Every change must have an issue in the tracker. If you are fixing a bug, there is probably one there already, but if not, create one. [Tips for searching tracker](./tracker/tips/index.md).

### Decide which branches the fix is required on

Expand Down Expand Up @@ -253,7 +253,7 @@ Issues identified as [[Security|security issues]] are resolved in a slightly dif
- If a developer has shared a solution as Git branches via Github, they should be asked to provide the solutions as [[How_to_create_a_patch|stand-alone patches]] attached to the issue and to [[#How to remove a branch from Github|remove the solution from Github]].
- contain details about the security problem in the commit message.
- Instead use generic terms like, "improve", "better handling of"
- The solution will not be integrated until the week before a [[Process#Stable_maintenance_cycles|minor release]] following the normal [[Release process|Release process]]. In short, the issue will be incorporated into the integration version, rebased, tested and made ready for release as a normal issue would, but not until as late as possible.
- The solution will not be integrated until the week before a [minor release](#Stable-maintenance-cycles) following the normal [[Release process|Release process]]. In short, the issue will be incorporated into the integration version, rebased, tested and made ready for release as a normal issue would, but not until as late as possible.
- Details of security issues will be shared with registered admins with the minor release.
- Details of security issues will not be publicly announced until one week after a minor release to allow admins to update.
Note that not all the labelled (minor) security issues are always handled following the procedure above. It's possible that, after discussion, it's decided a given issue is not a real Moodle security problem (say external disclosures/potential attacks using Moodle as vector, not as target, discussions revealing some private details). Those issues will be processed as normal issues, generating the needed user documentation if necessary and will be part of the habitual weekly releases.
Expand Down
98 changes: 98 additions & 0 deletions migratedPages.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,98 @@
const path = require('path');

const obsoleteDocs = [
"Setting_up_Eclipse",
"Setting_up_Netbeans",
];

/**
* A list of documents which have been migrated with their source and destination paths shown.
*/
const migratedDocs = {
"Access_API": "/docs/apis/access.md",
"Coding_style": "/general/development/policies/codingstyle/index.md",
"Communication_between_components": "/general/development/policies/component-communication/index.md",
"Developer_meeting_February_2022": "/general/community/meetings/202202.md",
"Developer_meetings": "/general/community/meetings.md",
"Integration_review": "/general/development/process/integration-review.md",
"Mission": "/general/community/mission.md",
"Moodle_research": "/general/community/research.md",
"Overview": "/general/community/intro.md",
"Peer_reviewing": "/general/development/process/peer-review.md",
"Process": "/general/development/process.md",
"Roadmap": "/general/community/roadmap.md",
"Tracker_intro": "/general/development/tracker.md",
"Tracker_tips": "/general/development/tracker/tips.md",
};

const isObsolete = (legacyPath) => obsoleteDocs.indexOf(legacyPath) !== -1;

/**
* Whether the specified path has been migrated.
*
* @returns {bool}
*/
const isMigrated = (legacyPath) => (typeof migratedDocs[legacyPath] !== 'undefined');

/**
* Get the path to the new doc from a legacy doc path.
*
* @param legacyPath {string}
* @returns {string}
*/
const getMigratedDoc = legacyPath => {
if (!isMigrated) {
return null;
}

const filename = migratedDocs[legacyPath];

if (filename.startsWith('/')) {
return filename.substr(1);
}

return filename;
};

/**
* Get the path to the new doc relative to the file it was in.
*
* This has to consider whether the file is in the same docs instance or not due to versioning.
*
* @param {strin} legacyPath
* @param {string} usedIn
* @returns {string}
*/
const getMigrationLink = (legacyPath, usedIn) => {
const replacementFile = getMigratedDoc(legacyPath);
if (!replacementFile) {
return null;
}

const relativeUsedIn = path.relative(process.env.PWD, usedIn);

const replacementIsGeneral = replacementFile.startsWith('general/');
const usedInIsGeneral = relativeUsedIn.startsWith('general/');
const bothGeneral = replacementIsGeneral && usedInIsGeneral;
const neitherGeneral = !replacementIsGeneral && !usedInIsGeneral;

if (bothGeneral || neitherGeneral) {
return path.relative(replacementFile, relativeUsedIn);
}

if (replacementFile.endsWith('index.md')) {
return `/${replacementFile.replace(/\/index\.md$/, '')}`;
}

if (replacementFile.endsWith('.md')) {
return `/${replacementFile.replace(/\.md$/, '')}`;
}

return `/${replacementFile}`;
};

module.exports = {
isMigrated,
isObsolete,
getMigrationLink,
};
43 changes: 38 additions & 5 deletions src/remark/legacyDocLinks.js
Original file line number Diff line number Diff line change
@@ -1,18 +1,51 @@
const visit = require('unist-util-visit');
const {isObsolete, isMigrated, getMigrationLink} = require('../../migratedPages');

const plugin = (options) => {
const transformer = async (ast) => {
visit(ast, 'linkReference', updateLink);
const transformer = async (ast, vfile) => {
visit(ast, 'linkReference', updateLink(vfile));
};
return transformer;
};

const getLinkFromString = string => {
const getLinkFromString = (vfile, string) => {
let [linkComponent] = string.split('|');

// Links never have spaces in them.
linkComponent = linkComponent.replaceAll(' ', '_');

// Split on the bookmark (if present).
let [pageComponent, bookmarkComponent] = linkComponent.split('#');

if (pageComponent) {
if (isMigrated(pageComponent)) {
if (bookmarkComponent) {
bookmarkComponent = `#${bookmarkComponent.replaceAll('_', '-')}`;
} else {
bookmarkComponent = '';
}
const migrationLink = getMigrationLink(pageComponent, vfile.path);
const replacement = `[${getDescriptionFromString(string)}](${migrationLink}${bookmarkComponent})`;

let message = `---\n`;
message += `- Use of legacy docs link found for migrated doc\n`;
message += `- File: \t ${vfile.path}\n`;
message += `- Found: \t [[${string}]]\n`;
message += `- Replacement: \t ${replacement}\n`;
message += `---\n`;
console.warn(message);

return migrationLink + bookmarkComponent;
} else if (isObsolete(pageComponent)) {
let message = `---\n`;
message += `- Use of obsoleted legacy doc link found for migrated doc\n`;
message += `- File: \t ${vfile.path}\n`;
message += `- Found: \t [[${string}]]\n`;
message += `---\n`;
console.warn(message);
}
}

if (linkComponent.substring(0, 1) === '#') {
// This is a relative link in the same page.
// Update it to meet the correct format.
Expand Down Expand Up @@ -53,7 +86,7 @@ const getDescriptionFromString = string => {
* @param {Number} index
* @param {Tree} parent
*/
const updateLink = (node, index, parent) => {
const updateLink = (vfile) => (node, index, parent) => {
if (parent.children[index - 1]?.type !== 'text') {
return null;
}
Expand All @@ -72,7 +105,7 @@ const updateLink = (node, index, parent) => {

const linkNode = {
type: 'link',
url: getLinkFromString(node.label),
url: getLinkFromString(vfile, node.label),
children: [{
type: 'text',
value: getDescriptionFromString(node.label),
Expand Down