Skip to content

Commit c7eb5c6

Browse files
authored
feat(ramps): rename onRamp* controller & service to ramps* (#7502)
## Explanation This PR renames all of the "on*" prefixed ramps controllers, services, interfaces, comments, variable names to just "Ramps". It also adds a build script and a watch script to improve the ramps development environment. Lastly, it updates the return structure of the geolocation fetch so that the correct values can be access and set to the ramp controller state. To use: place `metamask-mobile` and `core` in the same directory, then `cd core/packages/ramps-controller`, `yarn dev`. The watcher will build and replace in the metamask-mobile project. If the mobile watcher is running the app will auto-refresh. <!-- Thanks for your contribution! Take a moment to answer these questions so that reviewers have the information they need to properly understand your changes: * What is the current state of things and why does it need to change? * What is the solution your changes offer and how does it work? * Are there any changes whose purpose might not obvious to those unfamiliar with the domain? * If your primary goal was to update one package but you found you had to update another one along the way, why did you do so? * If you had to upgrade a dependency, why did you do so? --> ## References <!-- Are there any issues that this pull request is tied to? Are there other links that reviewers should consult to understand these changes better? Are there client or consumer pull requests to adopt any breaking changes? For example: * Fixes #12345 * Related to #67890 --> ## Changelog ### `@metamask/ramps-controller` #### Added - Renamed variables and added dev script ## Checklist - [ ] I've updated the test suite for new or updated code as appropriate - [ ] I've updated documentation (JSDoc, Markdown, etc.) for new or updated code as appropriate - [ ] I've communicated my changes to consumers by [updating changelogs for packages I've changed](https://github.com/MetaMask/core/tree/main/docs/contributing.md#updating-changelogs) - [ ] I've introduced [breaking changes](https://github.com/MetaMask/core/tree/main/docs/breaking-changes.md) in this PR and have prepared draft pull requests for clients and consumer packages to resolve them <!-- CURSOR_SUMMARY --> --- > [!NOTE] > Renames OnRampService to RampsService (including action namespaces), adds dev watch/link scripts for mobile integration, and fixes geolocation response handling. > > - **Core renames** > - Rename `OnRampService` → `RampsService` and `OnRampEnvironment` → `RampsEnvironment`. > - Update action namespaces/types from `OnRampService:*` → `RampsService:*` (e.g., `getGeolocation`). > - Adjust imports, messenger types/namespaces, and exports in `src/index.ts`, controller/service, and tests. > - **Bug fix** > - `RampsService#getGeolocation`: read and return response text within policy execution; validate non-empty result. > - **Dev tooling** > - Add `dev-watch.js` and `link-ramp-controller.js` to auto-build and copy `dist/` to `metamask-mobile`. > - Add `"dev": "node dev-watch.js"` script to `package.json`. > - **Changelog** > - Document added scripts, renames, and geolocation fix. > > <sup>Written by [Cursor Bugbot](https://cursor.com/dashboard?tab=bugbot) for commit 91c391d. This will update automatically on new commits. Configure [here](https://cursor.com/dashboard?tab=bugbot).</sup> <!-- /CURSOR_SUMMARY -->
1 parent f10f090 commit c7eb5c6

File tree

10 files changed

+305
-84
lines changed

10 files changed

+305
-84
lines changed

packages/ramps-controller/CHANGELOG.md

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,21 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
77

88
## [Unreleased]
99

10+
### Added
11+
12+
- Add `dev-watch.js` and `link-ramp-controller.js` scripts to auto-build and copy `dist/` into `metamask-mobile/node_modules/@metamask/ramps-controller`
13+
- Add `"dev": "node dev-watch.js"` script to `package.json`
14+
15+
### Changed
16+
17+
- Rename `OnRampService` to `RampsService` and `OnRampEnvironment` to `RampsEnvironment` ([#7316](https://github.com/MetaMask/core/pull/7316))
18+
- Rename action types from `OnRampService:*` to `RampsService:*` (e.g., `OnRampService:getGeolocation``RampsService:getGeolocation`)
19+
- Update imports, messenger types/namespaces, and exports in `src/index.ts`, controller/service files, and tests
20+
21+
### Fixed
22+
23+
- Fix `RampsService#getGeolocation` to read response text within the policy execution and return parsed text
24+
1025
## [1.0.0]
1126

1227
### Added
Lines changed: 78 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,78 @@
1+
/* eslint-disable */
2+
const { spawn } = require('child_process');
3+
const fs = require('fs');
4+
const path = require('path');
5+
6+
/**
7+
* Simple file watcher for ramps-controller development
8+
* Watches src/ directory and runs link script on changes
9+
*/
10+
11+
const srcDir = path.join(__dirname, 'src');
12+
const linkScript = path.join(__dirname, 'link-ramp-controller.js');
13+
14+
console.log('👀 Watching ramps-controller src/ directory...');
15+
console.log('📁 Press Ctrl+C to stop watching\n');
16+
17+
// Keep track of last build time to avoid rapid rebuilds
18+
let lastBuildTime = 0;
19+
const BUILD_THROTTLE_MS = 500; // Wait 500ms after last change before building
20+
21+
// Function to run the link script
22+
function runLinkScript() {
23+
return new Promise((resolve, reject) => {
24+
console.log('🔄 Changes detected, rebuilding and linking...');
25+
const child = spawn('node', [linkScript], {
26+
stdio: 'inherit',
27+
cwd: __dirname,
28+
});
29+
30+
child.on('close', (code) => {
31+
if (code !== 0) {
32+
console.error(`❌ Failed to rebuild and link (exit code ${code})`);
33+
reject(new Error(`Link script exited with code ${code}`));
34+
} else {
35+
console.log('✅ Rebuild and link complete\n');
36+
console.log('👀 Watching for changes...\n');
37+
resolve();
38+
}
39+
});
40+
41+
child.on('error', (error) => {
42+
console.error('❌ Failed to spawn link script:', error.message);
43+
reject(error);
44+
});
45+
});
46+
}
47+
48+
// Simple file watcher using fs.watch
49+
function watchDirectory(dir) {
50+
fs.watch(dir, { recursive: true }, (_eventType, filename) => {
51+
if (filename && (filename.endsWith('.ts') || filename.endsWith('.js'))) {
52+
const now = Date.now();
53+
if (now - lastBuildTime > BUILD_THROTTLE_MS) {
54+
lastBuildTime = now;
55+
// Debounce the build to avoid multiple rapid builds
56+
setTimeout(async () => {
57+
if (Date.now() - lastBuildTime >= BUILD_THROTTLE_MS) {
58+
await runLinkScript();
59+
}
60+
}, BUILD_THROTTLE_MS);
61+
}
62+
}
63+
});
64+
}
65+
66+
// Watch the src directory
67+
watchDirectory(srcDir);
68+
69+
// Also watch the link script itself
70+
fs.watchFile(linkScript, () => {
71+
console.log('🔄 Link script changed, will rebuild on next src change');
72+
});
73+
74+
// Initial build and link
75+
console.log('🏗️ Performing initial build and link...');
76+
runLinkScript().catch(() => {
77+
// Initial build errors are handled within runLinkScript
78+
});
Lines changed: 126 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,126 @@
1+
/* eslint-disable */
2+
const { execSync } = require('child_process');
3+
const fs = require('fs');
4+
const path = require('path');
5+
6+
// Helper function to check if path exists (replacement for deprecated fs.existsSync)
7+
function pathExistsSync(filePath) {
8+
try {
9+
fs.accessSync(filePath);
10+
return true;
11+
} catch {
12+
return false;
13+
}
14+
}
15+
16+
/**
17+
* Script to link ramps-controller for local development in MetaMask Mobile
18+
* This builds and copies the ramps-controller files to the mobile app's node_modules
19+
*/
20+
21+
const rampsControllerPath = __dirname;
22+
const mobileNodeModulesPath = path.join(
23+
__dirname,
24+
'..',
25+
'..',
26+
'..',
27+
'metamask-mobile',
28+
'node_modules',
29+
'@metamask',
30+
);
31+
const rampsControllerDestPath = path.join(
32+
mobileNodeModulesPath,
33+
'ramps-controller',
34+
);
35+
36+
// Always rebuild ramps-controller to ensure we have the latest changes
37+
const distPath = path.join(rampsControllerPath, 'dist');
38+
console.log('🔨 Building ramps-controller...');
39+
40+
// Clear any existing dist directory first
41+
if (pathExistsSync(distPath)) {
42+
fs.rmSync(distPath, { recursive: true, force: true });
43+
console.log('🗑️ Cleared existing build artifacts.');
44+
}
45+
46+
try {
47+
execSync('yarn build', {
48+
cwd: rampsControllerPath,
49+
stdio: 'inherit',
50+
env: { ...process.env, FORCE_COLOR: '1' }
51+
});
52+
console.log('✅ ramps-controller built successfully!');
53+
} catch (error) {
54+
console.error('❌ Failed to build ramps-controller:', error.message);
55+
process.exit(1);
56+
}
57+
58+
// Check if mobile app exists
59+
const mobilePath = path.join(__dirname, '..', '..', '..', 'metamask-mobile');
60+
if (!pathExistsSync(mobilePath)) {
61+
console.error('❌ MetaMask mobile app not found at expected location.');
62+
process.exit(1);
63+
}
64+
65+
console.log('🔗 Linking ramps-controller for local development...');
66+
67+
// Create @metamask directory if it doesn't exist
68+
if (!pathExistsSync(mobileNodeModulesPath)) {
69+
fs.mkdirSync(mobileNodeModulesPath, { recursive: true });
70+
}
71+
72+
// Remove existing link if it exists
73+
if (pathExistsSync(rampsControllerDestPath)) {
74+
fs.rmSync(rampsControllerDestPath, { recursive: true, force: true });
75+
}
76+
77+
// Files and directories to include (matches package.json "files" field + essential files)
78+
const INCLUDED_ENTRIES = new Set([
79+
'dist',
80+
'package.json',
81+
'LICENSE',
82+
'README.md',
83+
]);
84+
85+
// Copy a directory recursively
86+
function copyDir(src, dest) {
87+
if (!pathExistsSync(dest)) {
88+
fs.mkdirSync(dest, { recursive: true });
89+
}
90+
91+
const entries = fs.readdirSync(src, { withFileTypes: true });
92+
93+
for (const entry of entries) {
94+
const srcPath = path.join(src, entry.name);
95+
const destPath = path.join(dest, entry.name);
96+
97+
if (entry.isDirectory()) {
98+
copyDir(srcPath, destPath);
99+
} else {
100+
fs.copyFileSync(srcPath, destPath);
101+
}
102+
}
103+
}
104+
105+
// Copy only the files needed for the package (per package.json "files" field)
106+
fs.mkdirSync(rampsControllerDestPath, { recursive: true });
107+
108+
for (const entryName of INCLUDED_ENTRIES) {
109+
const srcPath = path.join(rampsControllerPath, entryName);
110+
const destPath = path.join(rampsControllerDestPath, entryName);
111+
112+
if (!pathExistsSync(srcPath)) {
113+
continue;
114+
}
115+
116+
const stat = fs.statSync(srcPath);
117+
if (stat.isDirectory()) {
118+
copyDir(srcPath, destPath);
119+
} else {
120+
fs.copyFileSync(srcPath, destPath);
121+
}
122+
}
123+
124+
console.log('✅ Successfully linked ramps-controller to MetaMask mobile app!');
125+
console.log(`📁 Copied to: ${rampsControllerDestPath}`);
126+
console.log('🔄 Re-run this script when you make changes to automatically rebuild and relink.');

packages/ramps-controller/package.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,7 @@
4040
"build:docs": "typedoc",
4141
"changelog:update": "../../scripts/update-changelog.sh @metamask/ramps-controller",
4242
"changelog:validate": "../../scripts/validate-changelog.sh @metamask/ramps-controller",
43+
"dev": "node dev-watch.js",
4344
"publish:preview": "yarn npm publish --tag preview",
4445
"since-latest-release": "../../scripts/since-latest-release.sh",
4546
"test": "NODE_OPTIONS=--experimental-vm-modules jest --reporters=jest-silent-reporter",

packages/ramps-controller/src/RampsController.test.ts

Lines changed: 4 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -6,9 +6,9 @@ import type {
66
MessengerEvents,
77
} from '@metamask/messenger';
88

9-
import type { OnRampServiceGetGeolocationAction } from './OnRampService-method-action-types';
109
import type { RampsControllerMessenger } from './RampsController';
1110
import { RampsController } from './RampsController';
11+
import type { RampsServiceGetGeolocationAction } from './RampsService-method-action-types';
1212

1313
describe('RampsController', () => {
1414
describe('constructor', () => {
@@ -116,7 +116,7 @@ describe('RampsController', () => {
116116
it('updates geolocation state when geolocation is fetched', async () => {
117117
await withController(async ({ controller, rootMessenger }) => {
118118
rootMessenger.registerActionHandler(
119-
'OnRampService:getGeolocation',
119+
'RampsService:getGeolocation',
120120
async () => 'US',
121121
);
122122

@@ -134,8 +134,7 @@ describe('RampsController', () => {
134134
*/
135135
type RootMessenger = Messenger<
136136
MockAnyNamespace,
137-
| MessengerActions<RampsControllerMessenger>
138-
| OnRampServiceGetGeolocationAction,
137+
MessengerActions<RampsControllerMessenger> | RampsServiceGetGeolocationAction,
139138
MessengerEvents<RampsControllerMessenger>
140139
>;
141140

@@ -179,7 +178,7 @@ function getMessenger(rootMessenger: RootMessenger): RampsControllerMessenger {
179178
});
180179
rootMessenger.delegate({
181180
messenger,
182-
actions: ['OnRampService:getGeolocation'],
181+
actions: ['RampsService:getGeolocation'],
183182
});
184183
return messenger;
185184
}

packages/ramps-controller/src/RampsController.ts

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ import type {
66
import { BaseController } from '@metamask/base-controller';
77
import type { Messenger } from '@metamask/messenger';
88

9-
import type { OnRampServiceGetGeolocationAction } from './OnRampService-method-action-types';
9+
import type { RampsServiceGetGeolocationAction } from './RampsService-method-action-types';
1010

1111
// === GENERAL ===
1212

@@ -73,7 +73,7 @@ export type RampsControllerActions = RampsControllerGetStateAction;
7373
/**
7474
* Actions from other messengers that {@link RampsController} calls.
7575
*/
76-
type AllowedActions = OnRampServiceGetGeolocationAction;
76+
type AllowedActions = RampsServiceGetGeolocationAction;
7777

7878
/**
7979
* Published when the state of {@link RampsController} changes.
@@ -141,12 +141,12 @@ export class RampsController extends BaseController<
141141

142142
/**
143143
* Updates the user's geolocation.
144-
* This method calls the OnRampService to get the geolocation
144+
* This method calls the RampsService to get the geolocation
145145
* and stores the result in state.
146146
*/
147147
async updateGeolocation(): Promise<void> {
148148
const geolocation = await this.messenger.call(
149-
'OnRampService:getGeolocation',
149+
'RampsService:getGeolocation',
150150
);
151151

152152
this.update((state) => {

packages/ramps-controller/src/OnRampService-method-action-types.ts renamed to packages/ramps-controller/src/RampsService-method-action-types.ts

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -3,20 +3,20 @@
33
* Do not edit manually.
44
*/
55

6-
import type { OnRampService } from './OnRampService';
6+
import type { RampsService } from './RampsService';
77

88
/**
99
* Makes a request to the API in order to retrieve the user's geolocation
1010
* based on their IP address.
1111
*
1212
* @returns The user's country/region code (e.g., "US-UT" for Utah, USA).
1313
*/
14-
export type OnRampServiceGetGeolocationAction = {
15-
type: `OnRampService:getGeolocation`;
16-
handler: OnRampService['getGeolocation'];
14+
export type RampsServiceGetGeolocationAction = {
15+
type: `RampsService:getGeolocation`;
16+
handler: RampsService['getGeolocation'];
1717
};
1818

1919
/**
20-
* Union of all OnRampService action types.
20+
* Union of all RampsService action types.
2121
*/
22-
export type OnRampServiceMethodActions = OnRampServiceGetGeolocationAction;
22+
export type RampsServiceMethodActions = RampsServiceGetGeolocationAction;

0 commit comments

Comments
 (0)