pull/5370/head
Your Name 5 months ago
commit f5a1f600c4
  1. 10
      apps/remix-ide-e2e/src/tests/etherscan_api.test.ts
  2. 17
      apps/remix-ide-e2e/src/tests/runAndDeploy_injected.test.ts
  3. 9
      apps/remix-ide-e2e/src/tests/terminal.test.ts
  4. 3
      apps/remix-ide/src/app/tabs/locales/en/filePanel.json
  5. 8
      libs/ghaction-helper/package.json
  6. 8
      libs/remix-analyzer/package.json
  7. 6
      libs/remix-astwalker/package.json
  8. 12
      libs/remix-debug/package.json
  9. 4
      libs/remix-lib/package.json
  10. 7
      libs/remix-simulator/package.json
  11. 6
      libs/remix-solidity/package.json
  12. 10
      libs/remix-tests/package.json
  13. 18
      libs/remix-ui/editor/src/lib/providers/inlineCompletionProvider.ts
  14. 15
      libs/remix-ui/editor/src/lib/remix-ui-editor.tsx
  15. 2
      libs/remix-ui/helper/src/lib/components/custom-dropdown.tsx
  16. 2
      libs/remix-ui/home-tab/src/lib/components/homeTabFeatured.tsx
  17. 4
      libs/remix-ui/workspace/src/lib/css/remix-ui-workspace.css
  18. 55
      libs/remix-ui/workspace/src/lib/remix-ui-workspace.tsx
  19. 4
      libs/remix-url-resolver/package.json
  20. 4
      libs/remix-ws-templates/package.json
  21. 4
      libs/remixd/package.json

@ -6,7 +6,7 @@ declare global {
interface Window { testplugin: { name: string, url: string }; } interface Window { testplugin: { name: string, url: string }; }
} }
module.exports = { const tests = {
'@disabled': true, '@disabled': true,
before: function (browser: NightwatchBrowser, done: VoidFunction) { before: function (browser: NightwatchBrowser, done: VoidFunction) {
init(browser, done, null) init(browser, done, null)
@ -58,6 +58,14 @@ module.exports = {
} }
} }
const branch = process.env.CIRCLE_BRANCH;
const isMasterBranch = branch === 'master';
module.exports = {
...(branch ? (isMasterBranch ? tests : {}) : tests),
};
const verifiedContract = ` const verifiedContract = `
// SPDX-License-Identifier: GPL-3.0 // SPDX-License-Identifier: GPL-3.0

@ -25,7 +25,7 @@ const checkAlerts = function (browser: NightwatchBrowser){
}) })
} }
module.exports = { const tests = {
'@disabled': true, '@disabled': true,
before: function (browser: NightwatchBrowser, done: VoidFunction) { before: function (browser: NightwatchBrowser, done: VoidFunction) {
init(browser, done) init(browser, done)
@ -50,10 +50,10 @@ module.exports = {
.pause(5000) .pause(5000)
.switchBrowserWindow(extension_url, 'MetaMask', (browser) => { .switchBrowserWindow(extension_url, 'MetaMask', (browser) => {
browser browser
.waitForElementVisible('*[data-testid="page-container-footer-next"]') .waitForElementVisible('*[data-testid="page-container-footer-next"]', 60000)
.click('*[data-testid="page-container-footer-next"]') // this connects the metamask account to remix .click('*[data-testid="page-container-footer-next"]') // this connects the metamask account to remix
.pause(2000) .pause(2000)
.waitForElementVisible('*[data-testid="page-container-footer-next"]') .waitForElementVisible('*[data-testid="page-container-footer-next"]', 60000)
.click('*[data-testid="page-container-footer-next"]') .click('*[data-testid="page-container-footer-next"]')
// .waitForElementVisible('*[data-testid="popover-close"]') // .waitForElementVisible('*[data-testid="popover-close"]')
// .click('*[data-testid="popover-close"]') // .click('*[data-testid="popover-close"]')
@ -162,7 +162,7 @@ module.exports = {
.perform((done) => { .perform((done) => {
browser.switchBrowserWindow(extension_url, 'MetaMask', (browser) => { browser.switchBrowserWindow(extension_url, 'MetaMask', (browser) => {
browser browser
.waitForElementPresent('[data-testid="page-container-footer-next"]') .waitForElementPresent('[data-testid="page-container-footer-next"]', 60000)
.click('[data-testid="page-container-footer-next"]') // approve the tx .click('[data-testid="page-container-footer-next"]') // approve the tx
.switchBrowserTab(0) // back to remix .switchBrowserTab(0) // back to remix
.waitForElementContainsText('*[data-id="terminalJournal"]', 'view on etherscan', 60000) .waitForElementContainsText('*[data-id="terminalJournal"]', 'view on etherscan', 60000)
@ -177,7 +177,7 @@ module.exports = {
.perform((done) => { // call delegate .perform((done) => { // call delegate
browser.switchBrowserWindow(extension_url, 'MetaMask', (browser) => { browser.switchBrowserWindow(extension_url, 'MetaMask', (browser) => {
browser browser
.waitForElementPresent('[data-testid="page-container-footer-next"]') .waitForElementPresent('[data-testid="page-container-footer-next"]', 60000)
.click('[data-testid="page-container-footer-next"]') // approve the tx .click('[data-testid="page-container-footer-next"]') // approve the tx
.switchBrowserTab(0) // back to remix .switchBrowserTab(0) // back to remix
.waitForElementContainsText('*[data-id="terminalJournal"]', 'view on etherscan', 60000) .waitForElementContainsText('*[data-id="terminalJournal"]', 'view on etherscan', 60000)
@ -232,6 +232,13 @@ module.exports = {
} }
} }
const branch = process.env.CIRCLE_BRANCH;
const isMasterBranch = branch === 'master';
module.exports = {
...(branch ? (isMasterBranch ? tests : {}) : tests),
};
const localsCheck = { const localsCheck = {
to: { to: {
value: '0x4B0897B0513FDC7C541B6D9D7E929C4E5364D2DB', value: '0x4B0897B0513FDC7C541B6D9D7E929C4E5364D2DB',

@ -2,6 +2,10 @@
import { NightwatchBrowser } from 'nightwatch' import { NightwatchBrowser } from 'nightwatch'
import init from '../helpers/init' import init from '../helpers/init'
const branch = process.env.CIRCLE_BRANCH;
const isMasterBranch = branch === 'master';
const runMasterTests: boolean = (branch ? (isMasterBranch ? true : false) : true)
module.exports = { module.exports = {
'@disabled': true, '@disabled': true,
before: function (browser: NightwatchBrowser, done: VoidFunction) { before: function (browser: NightwatchBrowser, done: VoidFunction) {
@ -209,6 +213,7 @@ module.exports = {
}, },
'Should run a script which log transaction and block using web3.js and ethers #group7': function (browser: NightwatchBrowser) { 'Should run a script which log transaction and block using web3.js and ethers #group7': function (browser: NightwatchBrowser) {
if (runMasterTests)
browser browser
.clickLaunchIcon('udapp') .clickLaunchIcon('udapp')
.switchEnvironment('basic-http-provider') .switchEnvironment('basic-http-provider')
@ -291,6 +296,7 @@ module.exports = {
}, },
'Should connect to mainnet fork and run web3.eth.getCode in the terminal #group9': function (browser: NightwatchBrowser) { 'Should connect to mainnet fork and run web3.eth.getCode in the terminal #group9': function (browser: NightwatchBrowser) {
if (runMasterTests)
browser browser
.clickLaunchIcon('udapp') .clickLaunchIcon('udapp')
.switchEnvironment('vm-mainnet-fork') .switchEnvironment('vm-mainnet-fork')
@ -305,6 +311,7 @@ module.exports = {
}, },
'Should connect to the sepolia fork and run web3.eth.getCode in the terminal #group9': function (browser: NightwatchBrowser) { 'Should connect to the sepolia fork and run web3.eth.getCode in the terminal #group9': function (browser: NightwatchBrowser) {
if (runMasterTests)
browser browser
.switchEnvironment('vm-custom-fork') .switchEnvironment('vm-custom-fork')
.waitForElementVisible('[data-id="vm-custom-fork-modal-footer-ok-react"]') .waitForElementVisible('[data-id="vm-custom-fork-modal-footer-ok-react"]')
@ -354,6 +361,7 @@ module.exports = {
console.log(resolver.addr(node)); console.log(resolver.addr(node));
} }
` `
if (runMasterTests) {
browser browser
// .clickLaunchIcon('udapp') // .clickLaunchIcon('udapp')
.switchEnvironment('vm-mainnet-fork') .switchEnvironment('vm-mainnet-fork')
@ -377,6 +385,7 @@ module.exports = {
}) })
.useCss() .useCss()
.waitForElementContainsText('*[data-id="terminalJournal"]', '0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045', 120000) .waitForElementContainsText('*[data-id="terminalJournal"]', '0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045', 120000)
}
}, },
'Should run free function which logs in the terminal #group10': function (browser: NightwatchBrowser) { 'Should run free function which logs in the terminal #group10': function (browser: NightwatchBrowser) {

@ -141,5 +141,6 @@
"filePanel.movingFolderFailed": "Moving Folder Failed", "filePanel.movingFolderFailed": "Moving Folder Failed",
"filePanel.movingFolderFailedMsg": "Unexpected error while moving folder: {src}", "filePanel.movingFolderFailedMsg": "Unexpected error while moving folder: {src}",
"filePanel.workspaceActions": "Workspace actions", "filePanel.workspaceActions": "Workspace actions",
"filePanel.saveCodeSample": "This code-sample workspace will not be persisted. Click here to save it." "filePanel.saveCodeSample": "This code-sample workspace will not be persisted. Click here to save it.",
"filePanel.updateSubmodules": "Update all submodules of repository. Click to pull dependencies."
} }

@ -1,6 +1,6 @@
{ {
"name": "@remix-project/ghaction-helper", "name": "@remix-project/ghaction-helper",
"version": "0.1.30", "version": "0.1.32",
"description": "Solidity Tests GitHub Action Helper", "description": "Solidity Tests GitHub Action Helper",
"main": "src/index.js", "main": "src/index.js",
"scripts": { "scripts": {
@ -19,17 +19,17 @@
}, },
"homepage": "https://github.com/ethereum/remix-project#readme", "homepage": "https://github.com/ethereum/remix-project#readme",
"devDependencies": { "devDependencies": {
"@remix-project/remix-solidity": "^0.5.36", "@remix-project/remix-solidity": "^0.5.38",
"@types/chai": "^4.3.4", "@types/chai": "^4.3.4",
"typescript": "^4.9.3" "typescript": "^4.9.3"
}, },
"dependencies": { "dependencies": {
"@ethereum-waffle/chai": "^3.4.4", "@ethereum-waffle/chai": "^3.4.4",
"@remix-project/remix-simulator": "^0.2.50", "@remix-project/remix-simulator": "^0.2.52",
"chai": "^4.3.7", "chai": "^4.3.7",
"ethers": "^5.7.2", "ethers": "^5.7.2",
"web3": "^4.1.1" "web3": "^4.1.1"
}, },
"types": "./src/index.d.ts", "types": "./src/index.d.ts",
"gitHead": "326585ffcef3a8846f2a1badf10beab1f73ee986" "gitHead": "35e1469e94bb370f5427d4ab230fcbd47c665e55"
} }

@ -1,6 +1,6 @@
{ {
"name": "@remix-project/remix-analyzer", "name": "@remix-project/remix-analyzer",
"version": "0.5.59", "version": "0.5.61",
"description": "Tool to perform static analysis on Solidity smart contracts", "description": "Tool to perform static analysis on Solidity smart contracts",
"scripts": { "scripts": {
"test": "./../../node_modules/.bin/ts-node --project ../../tsconfig.base.json --require tsconfig-paths/register ./../../node_modules/.bin/tape ./test/tests.ts" "test": "./../../node_modules/.bin/ts-node --project ../../tsconfig.base.json --require tsconfig-paths/register ./../../node_modules/.bin/tape ./test/tests.ts"
@ -25,8 +25,8 @@
"@ethereumjs/tx": "5.3.0", "@ethereumjs/tx": "5.3.0",
"@ethereumjs/util": "9.0.3", "@ethereumjs/util": "9.0.3",
"@ethereumjs/vm": "8.0.0", "@ethereumjs/vm": "8.0.0",
"@remix-project/remix-astwalker": "^0.0.80", "@remix-project/remix-astwalker": "^0.0.82",
"@remix-project/remix-lib": "^0.5.57", "@remix-project/remix-lib": "^0.5.59",
"async": "^2.6.2", "async": "^2.6.2",
"ethers": "^5.4.2", "ethers": "^5.4.2",
"ethjs-util": "^0.1.6", "ethjs-util": "^0.1.6",
@ -50,6 +50,6 @@
"typescript": "^3.7.5" "typescript": "^3.7.5"
}, },
"typings": "src/index.d.ts", "typings": "src/index.d.ts",
"gitHead": "326585ffcef3a8846f2a1badf10beab1f73ee986", "gitHead": "35e1469e94bb370f5427d4ab230fcbd47c665e55",
"main": "./src/index.js" "main": "./src/index.js"
} }

@ -1,6 +1,6 @@
{ {
"name": "@remix-project/remix-astwalker", "name": "@remix-project/remix-astwalker",
"version": "0.0.80", "version": "0.0.82",
"description": "Tool to walk through Solidity AST", "description": "Tool to walk through Solidity AST",
"main": "src/index.js", "main": "src/index.js",
"scripts": { "scripts": {
@ -37,7 +37,7 @@
"@ethereumjs/tx": "5.3.0", "@ethereumjs/tx": "5.3.0",
"@ethereumjs/util": "9.0.3", "@ethereumjs/util": "9.0.3",
"@ethereumjs/vm": "8.0.0", "@ethereumjs/vm": "8.0.0",
"@remix-project/remix-lib": "^0.5.57", "@remix-project/remix-lib": "^0.5.59",
"@types/tape": "^4.2.33", "@types/tape": "^4.2.33",
"async": "^2.6.2", "async": "^2.6.2",
"ethers": "^5.4.2", "ethers": "^5.4.2",
@ -53,6 +53,6 @@
"tap-spec": "^5.0.0" "tap-spec": "^5.0.0"
}, },
"typings": "src/index.d.ts", "typings": "src/index.d.ts",
"gitHead": "326585ffcef3a8846f2a1badf10beab1f73ee986", "gitHead": "35e1469e94bb370f5427d4ab230fcbd47c665e55",
"types": "./src/index.d.ts" "types": "./src/index.d.ts"
} }

@ -1,6 +1,6 @@
{ {
"name": "@remix-project/remix-debug", "name": "@remix-project/remix-debug",
"version": "0.5.50", "version": "0.5.52",
"description": "Tool to debug Ethereum transactions", "description": "Tool to debug Ethereum transactions",
"contributors": [ "contributors": [
{ {
@ -26,10 +26,10 @@
"@ethereumjs/tx": "5.3.0", "@ethereumjs/tx": "5.3.0",
"@ethereumjs/util": "9.0.3", "@ethereumjs/util": "9.0.3",
"@ethereumjs/vm": "8.0.0", "@ethereumjs/vm": "8.0.0",
"@remix-project/remix-astwalker": "^0.0.80", "@remix-project/remix-astwalker": "^0.0.82",
"@remix-project/remix-lib": "^0.5.57", "@remix-project/remix-lib": "^0.5.59",
"@remix-project/remix-simulator": "^0.2.50", "@remix-project/remix-simulator": "^0.2.52",
"@remix-project/remix-solidity": "^0.5.36", "@remix-project/remix-solidity": "^0.5.38",
"ansi-gray": "^0.1.1", "ansi-gray": "^0.1.1",
"async": "^2.6.2", "async": "^2.6.2",
"color-support": "^1.1.3", "color-support": "^1.1.3",
@ -69,6 +69,6 @@
}, },
"homepage": "https://github.com/ethereum/remix-project/tree/master/libs/remix-debug#readme", "homepage": "https://github.com/ethereum/remix-project/tree/master/libs/remix-debug#readme",
"typings": "src/index.d.ts", "typings": "src/index.d.ts",
"gitHead": "326585ffcef3a8846f2a1badf10beab1f73ee986", "gitHead": "35e1469e94bb370f5427d4ab230fcbd47c665e55",
"types": "./src/index.d.ts" "types": "./src/index.d.ts"
} }

@ -1,6 +1,6 @@
{ {
"name": "@remix-project/remix-lib", "name": "@remix-project/remix-lib",
"version": "0.5.57", "version": "0.5.59",
"description": "Library to various Remix tools", "description": "Library to various Remix tools",
"contributors": [ "contributors": [
{ {
@ -55,6 +55,6 @@
}, },
"homepage": "https://github.com/ethereum/remix-project/tree/master/libs/remix-lib#readme", "homepage": "https://github.com/ethereum/remix-project/tree/master/libs/remix-lib#readme",
"typings": "src/index.d.ts", "typings": "src/index.d.ts",
"gitHead": "326585ffcef3a8846f2a1badf10beab1f73ee986", "gitHead": "35e1469e94bb370f5427d4ab230fcbd47c665e55",
"types": "./src/index.d.ts" "types": "./src/index.d.ts"
} }

@ -1,6 +1,6 @@
{ {
"name": "@remix-project/remix-simulator", "name": "@remix-project/remix-simulator",
"version": "0.2.50", "version": "0.2.52",
"description": "Ethereum IDE and tools for the web", "description": "Ethereum IDE and tools for the web",
"contributors": [ "contributors": [
{ {
@ -22,7 +22,8 @@
"@ethereumjs/tx": "5.3.0", "@ethereumjs/tx": "5.3.0",
"@ethereumjs/util": "9.0.3", "@ethereumjs/util": "9.0.3",
"@ethereumjs/vm": "8.0.0", "@ethereumjs/vm": "8.0.0",
"@remix-project/remix-lib": "^0.5.57", "@metamask/eth-sig-util": "^7.0.2",
"@remix-project/remix-lib": "^0.5.59",
"ansi-gray": "^0.1.1", "ansi-gray": "^0.1.1",
"async": "^3.1.0", "async": "^3.1.0",
"body-parser": "^1.18.2", "body-parser": "^1.18.2",
@ -70,6 +71,6 @@
}, },
"homepage": "https://github.com/ethereum/remix-project/tree/master/libs/remix-simulator#readme", "homepage": "https://github.com/ethereum/remix-project/tree/master/libs/remix-simulator#readme",
"typings": "src/index.d.ts", "typings": "src/index.d.ts",
"gitHead": "326585ffcef3a8846f2a1badf10beab1f73ee986", "gitHead": "35e1469e94bb370f5427d4ab230fcbd47c665e55",
"types": "./src/index.d.ts" "types": "./src/index.d.ts"
} }

@ -1,6 +1,6 @@
{ {
"name": "@remix-project/remix-solidity", "name": "@remix-project/remix-solidity",
"version": "0.5.36", "version": "0.5.38",
"description": "Tool to load and run Solidity compiler", "description": "Tool to load and run Solidity compiler",
"main": "src/index.js", "main": "src/index.js",
"types": "src/index.d.ts", "types": "src/index.d.ts",
@ -19,7 +19,7 @@
"@ethereumjs/tx": "5.3.0", "@ethereumjs/tx": "5.3.0",
"@ethereumjs/util": "9.0.3", "@ethereumjs/util": "9.0.3",
"@ethereumjs/vm": "8.0.0", "@ethereumjs/vm": "8.0.0",
"@remix-project/remix-lib": "^0.5.57", "@remix-project/remix-lib": "^0.5.59",
"async": "^2.6.2", "async": "^2.6.2",
"eslint-scope": "^5.0.0", "eslint-scope": "^5.0.0",
"ethers": "^5.4.2", "ethers": "^5.4.2",
@ -57,5 +57,5 @@
}, },
"homepage": "https://github.com/ethereum/remix-project/tree/master/libs/remix-solidity#readme", "homepage": "https://github.com/ethereum/remix-project/tree/master/libs/remix-solidity#readme",
"typings": "src/index.d.ts", "typings": "src/index.d.ts",
"gitHead": "326585ffcef3a8846f2a1badf10beab1f73ee986" "gitHead": "35e1469e94bb370f5427d4ab230fcbd47c665e55"
} }

@ -1,6 +1,6 @@
{ {
"name": "@remix-project/remix-tests", "name": "@remix-project/remix-tests",
"version": "0.2.50", "version": "0.2.52",
"description": "Tool to test Solidity smart contracts", "description": "Tool to test Solidity smart contracts",
"main": "src/index.js", "main": "src/index.js",
"types": "./src/index.d.ts", "types": "./src/index.d.ts",
@ -41,9 +41,9 @@
"@ethereumjs/tx": "5.3.0", "@ethereumjs/tx": "5.3.0",
"@ethereumjs/util": "9.0.3", "@ethereumjs/util": "9.0.3",
"@ethereumjs/vm": "8.0.0", "@ethereumjs/vm": "8.0.0",
"@remix-project/remix-lib": "^0.5.57", "@remix-project/remix-lib": "^0.5.59",
"@remix-project/remix-simulator": "^0.2.50", "@remix-project/remix-simulator": "^0.2.52",
"@remix-project/remix-solidity": "^0.5.36", "@remix-project/remix-solidity": "^0.5.38",
"@remix-project/remix-url-resolver": "^0.0.42", "@remix-project/remix-url-resolver": "^0.0.42",
"ansi-gray": "^0.1.1", "ansi-gray": "^0.1.1",
"async": "^2.6.0", "async": "^2.6.0",
@ -89,5 +89,5 @@
"@ethereumjs/trie": "6.2.0" "@ethereumjs/trie": "6.2.0"
}, },
"typings": "src/index.d.ts", "typings": "src/index.d.ts",
"gitHead": "326585ffcef3a8846f2a1badf10beab1f73ee986" "gitHead": "35e1469e94bb370f5427d4ab230fcbd47c665e55"
} }

@ -4,6 +4,7 @@ import { CompletionTimer } from './completionTimer';
import axios, { AxiosResponse } from 'axios' import axios, { AxiosResponse } from 'axios'
import { slice } from 'lodash'; import { slice } from 'lodash';
import { activateService } from '@remixproject/plugin-utils';
const _paq = (window._paq = window._paq || []) const _paq = (window._paq = window._paq || [])
const controller = new AbortController(); const controller = new AbortController();
@ -14,6 +15,9 @@ export class RemixInLineCompletionProvider implements monacoTypes.languages.Inli
props: EditorUIProps props: EditorUIProps
monaco: any monaco: any
completionEnabled: boolean completionEnabled: boolean
task: string
currentCompletion
constructor(props: any, monaco: any) { constructor(props: any, monaco: any) {
this.props = props this.props = props
this.monaco = monaco this.monaco = monaco
@ -28,6 +32,7 @@ export class RemixInLineCompletionProvider implements monacoTypes.languages.Inli
const lineRange = model.getFullModelRange().setStartPosition(lineNumber, 1).setEndPosition(lineNumber + 1, 1); const lineRange = model.getFullModelRange().setStartPosition(lineNumber, 1).setEndPosition(lineNumber + 1, 1);
return model.getValueInRange(lineRange); return model.getValueInRange(lineRange);
} }
// get text before the position of the completion // get text before the position of the completion
const word = model.getValueInRange({ const word = model.getValueInRange({
startLineNumber: 1, startLineNumber: 1,
@ -65,6 +70,7 @@ export class RemixInLineCompletionProvider implements monacoTypes.languages.Inli
// use the code generation model, only take max 1000 word as context // use the code generation model, only take max 1000 word as context
this.props.plugin.call('terminal', 'log', { type: 'aitypewriterwarning', value: 'Solcoder - generating code for following comment: ' + ask.replace('///', '') }) this.props.plugin.call('terminal', 'log', { type: 'aitypewriterwarning', value: 'Solcoder - generating code for following comment: ' + ask.replace('///', '') })
this.task = 'code_generation'
const data = await this.props.plugin.call('solcoder', 'code_generation', word) const data = await this.props.plugin.call('solcoder', 'code_generation', word)
const parsedData = data[0].trimStart() //JSON.parse(data).trimStart() const parsedData = data[0].trimStart() //JSON.parse(data).trimStart()
@ -103,15 +109,15 @@ export class RemixInLineCompletionProvider implements monacoTypes.languages.Inli
if (word.replace(/ +$/, '').endsWith('\n')){ if (word.replace(/ +$/, '').endsWith('\n')){
// Code insertion // Code insertion
try { try {
this.task = 'code_insertion'
const output = await this.props.plugin.call('solcoder', 'code_insertion', word, word_after) const output = await this.props.plugin.call('solcoder', 'code_insertion', word, word_after)
const generatedText = output[0] // no need to clean it. should already be const generatedText = output[0] // no need to clean it. should already be
const item: monacoTypes.languages.InlineCompletion = { const item: monacoTypes.languages.InlineCompletion = {
insertText: generatedText insertText: generatedText
}; };
this.completionEnabled = false this.completionEnabled = false
const handleCompletionTimer = new CompletionTimer(5000, () => { this.completionEnabled = true }); const handleCompletionTimer = new CompletionTimer(1000, () => { this.completionEnabled = true });
handleCompletionTimer.start() handleCompletionTimer.start()
return { return {
@ -127,6 +133,7 @@ export class RemixInLineCompletionProvider implements monacoTypes.languages.Inli
let result let result
try { try {
// Code completion // Code completion
this.task = 'code_completion'
const output = await this.props.plugin.call('solcoder', 'code_completion', word) const output = await this.props.plugin.call('solcoder', 'code_completion', word)
const generatedText = output[0] const generatedText = output[0]
let clean = generatedText let clean = generatedText
@ -168,14 +175,15 @@ export class RemixInLineCompletionProvider implements monacoTypes.languages.Inli
} }
handleItemDidShow?(completions: monacoTypes.languages.InlineCompletions<monacoTypes.languages.InlineCompletion>, item: monacoTypes.languages.InlineCompletion, updatedInsertText: string): void { handleItemDidShow?(completions: monacoTypes.languages.InlineCompletions<monacoTypes.languages.InlineCompletion>, item: monacoTypes.languages.InlineCompletion, updatedInsertText: string): void {
this.currentCompletion = { 'item':item, 'task':this.task }
_paq.push(['trackEvent', 'ai', 'solcoder', this.task + '_did_show'])
} }
handlePartialAccept?(completions: monacoTypes.languages.InlineCompletions<monacoTypes.languages.InlineCompletion>, item: monacoTypes.languages.InlineCompletion, acceptedCharacters: number): void { handlePartialAccept?(completions: monacoTypes.languages.InlineCompletions<monacoTypes.languages.InlineCompletion>, item: monacoTypes.languages.InlineCompletion, acceptedCharacters: number): void {
_paq.push(['trackEvent', 'ai', 'solcoder', this.task + '_partial_accept'])
} }
freeInlineCompletions(completions: monacoTypes.languages.InlineCompletions<monacoTypes.languages.InlineCompletion>): void { freeInlineCompletions(completions: monacoTypes.languages.InlineCompletions<monacoTypes.languages.InlineCompletion>): void {
} }
groupId?: string; groupId?: string;
yieldsToGroupIds?: string[]; yieldsToGroupIds?: string[];
toString?(): string { toString?(): string {

@ -368,6 +368,8 @@ export const EditorUI = (props: EditorUIProps) => {
} }
}, [props.currentFile, props.isDiff]) }, [props.currentFile, props.isDiff])
const inlineCompletionProvider = new RemixInLineCompletionProvider(props, monacoRef.current)
const convertToMonacoDecoration = (decoration: lineText | sourceAnnotation | sourceMarker, typeOfDecoration: string) => { const convertToMonacoDecoration = (decoration: lineText | sourceAnnotation | sourceMarker, typeOfDecoration: string) => {
if (typeOfDecoration === 'sourceAnnotationsPerFile') { if (typeOfDecoration === 'sourceAnnotationsPerFile') {
decoration = decoration as sourceAnnotation decoration = decoration as sourceAnnotation
@ -700,6 +702,17 @@ export const EditorUI = (props: EditorUIProps) => {
} }
}) })
editor.onDidChangeModelContent((e) => {
if (inlineCompletionProvider.currentCompletion) {
const changes = e.changes;
// Check if the change matches the current completion
if (changes.some(change => change.text === inlineCompletionProvider.currentCompletion.item.insertText)) {
_paq.push(['trackEvent', 'ai', 'solcoder', inlineCompletionProvider.currentCompletion.task + '_accepted'])
inlineCompletionProvider.currentCompletion = null;
}
}
});
// add context menu items // add context menu items
const zoominAction = { const zoominAction = {
id: 'zoomIn', id: 'zoomIn',
@ -1003,7 +1016,7 @@ export const EditorUI = (props: EditorUIProps) => {
monacoRef.current.languages.registerReferenceProvider('remix-solidity', new RemixReferenceProvider(props, monaco)) monacoRef.current.languages.registerReferenceProvider('remix-solidity', new RemixReferenceProvider(props, monaco))
monacoRef.current.languages.registerHoverProvider('remix-solidity', new RemixHoverProvider(props, monaco)) monacoRef.current.languages.registerHoverProvider('remix-solidity', new RemixHoverProvider(props, monaco))
monacoRef.current.languages.registerCompletionItemProvider('remix-solidity', new RemixCompletionProvider(props, monaco)) monacoRef.current.languages.registerCompletionItemProvider('remix-solidity', new RemixCompletionProvider(props, monaco))
monacoRef.current.languages.registerInlineCompletionsProvider('remix-solidity', new RemixInLineCompletionProvider(props, monaco)) monacoRef.current.languages.registerInlineCompletionsProvider('remix-solidity', inlineCompletionProvider)
monaco.languages.registerCodeActionProvider('remix-solidity', new RemixCodeActionProvider(props, monaco)) monaco.languages.registerCodeActionProvider('remix-solidity', new RemixCodeActionProvider(props, monaco))
loadTypes(monacoRef.current) loadTypes(monacoRef.current)

@ -29,7 +29,7 @@ export const CustomToggle = React.forwardRef(
className={className.replace('dropdown-toggle', '')} className={className.replace('dropdown-toggle', '')}
> >
<div className="d-flex"> <div className="d-flex">
<div className="mr-auto text-nowrap overflow-hidden">{children}</div> <div className="mr-auto text-nowrap text-truncate overflow-hidden">{children}</div>
{icon && ( {icon && (
<div className="pr-1"> <div className="pr-1">
<i className={`${icon} pr-1`}></i> <i className={`${icon} pr-1`}></i>

@ -12,7 +12,7 @@ function HomeTabFeatured() {
const themeFilter = useContext(ThemeContext) const themeFilter = useContext(ThemeContext)
return ( return (
<div className="pt-1 pl-2 h-100" id="hTFeaturedeSection"> <div className="pt-1 pl-2" id="hTFeaturedeSection">
<div className="mb-2 remix_ui-carousel-container"> <div className="mb-2 remix_ui-carousel-container">
<div className="w-100 d-flex flex-column rounded-3 remix_ui-carouselbox"> <div className="w-100 d-flex flex-column rounded-3 remix_ui-carouselbox">
<ThemeContext.Provider value={themeFilter}> <ThemeContext.Provider value={themeFilter}>

@ -77,6 +77,10 @@
background: var(--custom-select); background: var(--custom-select);
} }
.branches-dropdown {
max-width: 16rem;
}
.custom-dropdown-items a { .custom-dropdown-items a {
border-radius: .25rem; border-radius: .25rem;
text-transform: none; text-transform: none;

@ -1347,25 +1347,43 @@ export function Workspace() {
</div> </div>
{ selectedWorkspace && ( { selectedWorkspace && (
<div className={`bg-light border-top ${selectedWorkspace.isGitRepo && currentBranch ? 'd-block' : 'd-none'}`} data-id="workspaceGitPanel"> <div className={`bg-light border-top ${selectedWorkspace.isGitRepo && currentBranch ? 'd-block' : 'd-none'}`} data-id="workspaceGitPanel">
<div className="d-flex justify-space-between p-1"> <div className="d-flex justify-content-between p-1">
<div className="mr-auto text-uppercase text-dark pt-2 px-1">GIT</div> <div className="text-uppercase text-dark pt-1 px-1">GIT</div>
{ selectedWorkspace.hasGitSubmodules? { selectedWorkspace.hasGitSubmodules?
<div className="pt-1 mr-1"> <CustomTooltip
{global.fs.browser.isRequestingCloning ? <div style={{ height: 30, minWidth: 165 }} className='btn btn-sm border text-muted small'><i className="fad fa-spinner fa-spin"></i> updating submodules</div> : placement="top"
<div style={{ height: 30, minWidth: 165 }} onClick={updateSubModules} data-id='updatesubmodules' className={`btn btn-sm border small ${highlightUpdateSubmodules ? 'text-warning' : 'text-muted'}`}>update submodules</div>} tooltipId="updateSubmodules"
tooltipClasses="text-nowrap"
tooltipText={<FormattedMessage id="filePanel.updateSubmodules" />}
>
<div className="pr-1">
{ global.fs.browser.isRequestingCloning ? <button style={{ height: 30, minWidth: "9rem" }} className='btn btn-sm border text-dark'>
<i className="fad fa-spinner fa-spin"></i>
Updating submodules
</button> :
<button style={{ height: 30, minWidth: "9rem" }} onClick={updateSubModules} data-id='updatesubmodules' className={`btn btn-sm border ${highlightUpdateSubmodules ? 'text-warning' : 'text-dark'}`}>
Update submodules
</button> }
</div> </div>
: null} </CustomTooltip>
<div className="pt-1 mr-1" data-id="workspaceGitBranchesDropdown"> : null
<Dropdown style={{ height: 30, minWidth: 80 }} onToggle={toggleBranches} show={showBranches} drop={'up'}> }
<CustomTooltip
placement="right"
tooltipId="branchesDropdown"
tooltipClasses="text-nowrap"
tooltipText={'Current branch: ' + currentBranch || 'Branches'}
>
<div className="pt-0 mr-2" data-id="workspaceGitBranchesDropdown">
<Dropdown style={{ height: 30, maxWidth: "6rem", minWidth: "6rem" }} onToggle={toggleBranches} show={showBranches} drop={'up'}>
<Dropdown.Toggle <Dropdown.Toggle
as={CustomToggle} as={CustomToggle}
id="dropdown-custom-components" id="dropdown-custom-components"
className="btn btn-light btn-block w-100 d-inline-block border border-dark form-control h-100 p-0 pl-2 pr-2 text-dark" className="btn btn-sm btn-light d-inline-block border border-dark form-control h-100 p-0 pl-2 pr-2 text-dark"
icon={null} icon={null}
> >
{global.fs.browser.isRequestingCloning ? <i className="fad fa-spinner fa-spin"></i> : (currentBranch && currentBranch.name) || '-none-'} {global.fs.browser.isRequestingCloning ? <i className="fad fa-spinner fa-spin"></i> : currentBranch.name || '-none-'}
</Dropdown.Toggle> </Dropdown.Toggle>
<Dropdown.Menu as={CustomMenu} className="custom-dropdown-items branches-dropdown"> <Dropdown.Menu as={CustomMenu} className="custom-dropdown-items branches-dropdown">
<div data-id="custom-dropdown-menu"> <div data-id="custom-dropdown-menu">
<div className="d-flex text-dark" style={{ fontSize: 14, fontWeight: 'bold' }}> <div className="d-flex text-dark" style={{ fontSize: 14, fontWeight: 'bold' }}>
@ -1403,8 +1421,8 @@ export function Workspace() {
}} }}
title={intl.formatMessage({ id: `filePanel.switchToBranch${branch.remote ? 'Title1' : 'Title2'}` })} title={intl.formatMessage({ id: `filePanel.switchToBranch${branch.remote ? 'Title1' : 'Title2'}` })}
> >
<div data-id={`workspaceGit-${branch.remote ? `${branch.remote.name}/${branch.name}` : branch.name}`}> <div data-id={`workspaceGit-${branch.remote ? `${branch.remote}/${branch.name}` : branch.name}`}>
{currentBranch && currentBranch.name === branch.name && !branch.remote ? ( {currentBranch.name === branch.name && !branch.remote ? (
<span> <span>
&#10003; <i className="far fa-code-branch"></i> &#10003; <i className="far fa-code-branch"></i>
<span className="pl-1">{branch.name}</span> <span className="pl-1">{branch.name}</span>
@ -1412,7 +1430,7 @@ export function Workspace() {
) : ( ) : (
<span className="pl-3"> <span className="pl-3">
<i className={`far ${branch.remote ? 'fa-cloud' : 'fa-code-branch'}`}></i> <i className={`far ${branch.remote ? 'fa-cloud' : 'fa-code-branch'}`}></i>
<span className="pl-1">{branch.remote ? `${branch.remote.name}/${branch.name}` : branch.name}</span> <span className="pl-1">{branch.remote ? `${branch.remote}/${branch.name}` : branch.name}</span>
</span> </span>
)} )}
</div> </div>
@ -1424,23 +1442,22 @@ export function Workspace() {
<div className="pl-1 pr-1" data-id="workspaceGitCreateNewBranch"> <div className="pl-1 pr-1" data-id="workspaceGitCreateNewBranch">
<i className="fas fa-code-branch pr-2"></i> <i className="fas fa-code-branch pr-2"></i>
<span> <span>
<FormattedMessage id="filePanel.createBranch" />: {branchFilter} from '{currentBranch && currentBranch.name}' <FormattedMessage id="filePanel.createBranch" />: {branchFilter} from '{currentBranch.name}'
</span> </span>
</div> </div>
</Dropdown.Item> </Dropdown.Item>
)} )}
</div> </div>
{(selectedWorkspace.branches || []).length > 4 && ( {(selectedWorkspace.branches || []).length > 4 && (
<div className="text-center border-top pt-2"> <button className="btn btn-sm w-100" style={{ cursor: "pointer" }} onClick={showAllBranches}>
<label style={{ fontSize: 12, cursor: 'pointer' }} onClick={showAllBranches}>
<FormattedMessage id="filePanel.viewAllBranches" /> <FormattedMessage id="filePanel.viewAllBranches" />
</label> </button>
</div>
)} )}
</div> </div>
</Dropdown.Menu> </Dropdown.Menu>
</Dropdown> </Dropdown>
</div> </div>
</CustomTooltip>
</div> </div>
</div> </div>
)} )}

@ -1,6 +1,6 @@
{ {
"name": "@remix-project/remix-url-resolver", "name": "@remix-project/remix-url-resolver",
"version": "0.0.79", "version": "0.0.81",
"description": "Solidity import url resolver engine", "description": "Solidity import url resolver engine",
"main": "src/index.js", "main": "src/index.js",
"types": "src/index.d.ts", "types": "src/index.d.ts",
@ -41,5 +41,5 @@
"typescript": "^3.1.6" "typescript": "^3.1.6"
}, },
"typings": "src/index.d.ts", "typings": "src/index.d.ts",
"gitHead": "326585ffcef3a8846f2a1badf10beab1f73ee986" "gitHead": "35e1469e94bb370f5427d4ab230fcbd47c665e55"
} }

@ -1,6 +1,6 @@
{ {
"name": "@remix-project/remix-ws-templates", "name": "@remix-project/remix-ws-templates",
"version": "1.0.44", "version": "1.0.46",
"description": "Create a Remix IDE workspace using different templates", "description": "Create a Remix IDE workspace using different templates",
"main": "src/index.js", "main": "src/index.js",
"types": "src/index.d.ts", "types": "src/index.d.ts",
@ -24,5 +24,5 @@
"ethers": "^5.4.2", "ethers": "^5.4.2",
"web3": "^4.1.1" "web3": "^4.1.1"
}, },
"gitHead": "326585ffcef3a8846f2a1badf10beab1f73ee986" "gitHead": "35e1469e94bb370f5427d4ab230fcbd47c665e55"
} }

@ -1,6 +1,6 @@
{ {
"name": "@remix-project/remixd", "name": "@remix-project/remixd",
"version": "0.6.33", "version": "0.6.34",
"description": "remix server: allow accessing file system from remix.ethereum.org and start a dev environment (see help section)", "description": "remix server: allow accessing file system from remix.ethereum.org and start a dev environment (see help section)",
"main": "index.js", "main": "index.js",
"types": "./index.d.ts", "types": "./index.d.ts",
@ -27,11 +27,11 @@
}, },
"homepage": "https://github.com/ethereum/remix-project#readme", "homepage": "https://github.com/ethereum/remix-project#readme",
"dependencies": { "dependencies": {
"@remix-project/remix-solidity": "^0.5.36",
"@remixproject/plugin": "0.3.33", "@remixproject/plugin": "0.3.33",
"@remixproject/plugin-api": "0.3.33", "@remixproject/plugin-api": "0.3.33",
"@remixproject/plugin-utils": "0.3.33", "@remixproject/plugin-utils": "0.3.33",
"@remixproject/plugin-ws": "0.3.33", "@remixproject/plugin-ws": "0.3.33",
"@remix-project/remix-solidity": "^0.5.36",
"axios": "1.6.0", "axios": "1.6.0",
"chokidar": "^2.1.8", "chokidar": "^2.1.8",
"commander": "^9.4.1", "commander": "^9.4.1",

Loading…
Cancel
Save