diff --git a/.github/config.json b/.github/config.json index c67bf7d48b..ebaa14d1a8 100644 --- a/.github/config.json +++ b/.github/config.json @@ -1 +1 @@ -{"runners":[{"versioning":{"source":"milestones","type":"SemVer"},"prereleaseName":"alpha","issue":{"labels":{"Error Handling":{"conditions":[],"requires":1},"Team Managers Pod":{"conditions":[{"label":"SSO","type":"hasLabel","value":true},{"label":"RBAC","type":"hasLabel","value":true},{"label":"Audit Logs","type":"hasLabel","value":true},{"label":"Airgap","type":"hasLabel","value":true},{"label":"Enterprise Edition","type":"hasLabel","value":true},{"label":"SCIM","type":"hasLabel","value":true},{"label":"Invite flow","type":"hasLabel","value":true},{"label":"User Profile","type":"hasLabel","value":true},{"label":"Admin Settings","type":"hasLabel","value":true},{"label":"Workspace settings","type":"hasLabel","value":true}],"requires":1},"New Developers Pod":{"conditions":[{"label":"Omnibar","type":"hasLabel","value":true},{"label":"Telemetry","type":"hasLabel","value":true},{"label":"Entity Explorer","type":"hasLabel","value":true},{"label":"IDE","type":"hasLabel","value":true},{"label":"i18n","type":"hasLabel","value":true},{"label":"IDE Navigation","type":"hasLabel","value":true},{"label":"In App Comms","type":"hasLabel","value":true},{"label":"App setting","type":"hasLabel","value":true}],"requires":1},"BE Coders Pod":{"conditions":[{"label":"SAAS Plugins","type":"hasLabel","value":true},{"label":"Data Platform Pod","type":"hasLabel","value":true},{"label":"Integrations Pod","type":"hasLabel","value":true}],"requires":1},"FE Coders Pod":{"conditions":[{"label":"JS Linting & Errors","type":"hasLabel","value":true},{"label":"Debugger","type":"hasLabel","value":true},{"label":"Autocomplete","type":"hasLabel","value":true},{"label":"Evaluated Value","type":"hasLabel","value":true},{"label":"Slash Command","type":"hasLabel","value":true},{"label":"New JS Function","type":"hasLabel","value":true},{"label":"JS Usability","type":"hasLabel","value":true},{"label":"OnPageLoad","type":"hasLabel","value":true},{"label":"Framework Functions","type":"hasLabel","value":true},{"label":"JS Objects","type":"hasLabel","value":true},{"label":"JS Evaluation","type":"hasLabel","value":true},{"label":"AST-frontend","type":"hasLabel","value":true},{"label":"Custom JS Libraries","type":"hasLabel","value":true},{"label":"Action Selector","type":"hasLabel","value":true},{"label":"Widget setter method","type":"hasLabel","value":true},{"label":"Error Handling","type":"hasLabel","value":true}],"requires":1},"App Viewers Pod":{"conditions":[{"label":"Button Widget","type":"hasLabel","value":true},{"label":"Chart Widget","type":"hasLabel","value":true},{"label":"Container Widget","type":"hasLabel","value":true},{"label":"Date Picker Widget","type":"hasLabel","value":true},{"label":"Select Widget","type":"hasLabel","value":true},{"label":"File Picker Widget","type":"hasLabel","value":true},{"label":"Form Widget","type":"hasLabel","value":true},{"label":"Image Widget","type":"hasLabel","value":true},{"label":"Input Widget","type":"hasLabel","value":true},{"label":"List Widget","type":"hasLabel","value":true},{"label":"MultiSelect Widget","type":"hasLabel","value":true},{"label":"Map Widget","type":"hasLabel","value":true},{"label":"Modal Widget","type":"hasLabel","value":true},{"label":"Radio Widget","type":"hasLabel","value":true},{"label":"Rich Text Editor Widget","type":"hasLabel","value":true},{"label":"Tab Widget","type":"hasLabel","value":true},{"label":"Table Widget","type":"hasLabel","value":true},{"label":"Text Widget","type":"hasLabel","value":true},{"label":"Video Widget","type":"hasLabel","value":true},{"label":"iFrame","type":"hasLabel","value":true},{"label":"Menu Button","type":"hasLabel","value":true},{"label":"Rating","type":"hasLabel","value":true},{"label":"Widget Validation","type":"hasLabel","value":true},{"label":"reallabel","type":"hasLabel","value":true},{"label":"New Widget","type":"hasLabel","value":true},{"label":"Switch widget","type":"hasLabel","value":true},{"label":"Audio Widget","type":"hasLabel","value":true},{"label":"Icon Button Widget","type":"hasLabel","value":true},{"label":"Stat Box Widget","type":"hasLabel","value":true},{"label":"Voice Recorder Widget","type":"hasLabel","value":true},{"label":"Calendar Widget","type":"hasLabel","value":true},{"label":"Menu Button Widget","type":"hasLabel","value":true},{"label":"Divider Widget","type":"hasLabel","value":true},{"label":"Rating Widget","type":"hasLabel","value":true},{"label":"View Mode","type":"hasLabel","value":true},{"label":"Widget Property","type":"hasLabel","value":true},{"label":"Document Viewer Widget","type":"hasLabel","value":true},{"label":"Radio Group Widget","type":"hasLabel","value":true},{"label":"Currency Input Widget","type":"hasLabel","value":true},{"label":"TreeSelect","type":"hasLabel","value":true},{"label":"MultiTree Select Widget","type":"hasLabel","value":true},{"label":"Phone Input Widget","type":"hasLabel","value":true},{"label":"JSON Form","type":"hasLabel","value":true},{"label":"All Widgets","type":"hasLabel","value":true},{"label":"Button Group widget","type":"hasLabel","value":true},{"label":"Progress bar widget","type":"hasLabel","value":true},{"label":"Audio Recorder Widget","type":"hasLabel","value":true},{"label":"Camera Widget","type":"hasLabel","value":true},{"label":"Table Widget V2","type":"hasLabel","value":true},{"label":"Branding","type":"hasLabel","value":true},{"label":"Map Chart Widget","type":"hasLabel","value":true},{"label":"Code Scanner Widget","type":"hasLabel","value":true},{"label":"Widget keyboard accessibility","type":"hasLabel","value":true},{"label":"List Widget V2","type":"hasLabel","value":true},{"label":"Slider Widget","type":"hasLabel","value":true},{"label":"One-click Binding","type":"hasLabel","value":true},{"label":"Old widget version","type":"hasLabel","value":true},{"label":"Widget Discoverability","type":"hasLabel","value":true},{"label":"Custom widgets","type":"hasLabel","value":true},{"label":"Switch Group Widget","type":"hasLabel","value":true},{"label":"Checkbox Group widget","type":"hasLabel","value":true},{"label":"Checkbox Widget","type":"hasLabel","value":true},{"label":"Table Inline Edit","type":"hasLabel","value":true}],"requires":1},"UI Builders Pod":{"conditions":[{"label":"Property Pane","type":"hasLabel","value":true},{"label":"Copy Paste","type":"hasLabel","value":true},{"label":"Drag & Drop","type":"hasLabel","value":true},{"label":"Undo/Redo","type":"hasLabel","value":true},{"label":"Widgets Pane","type":"hasLabel","value":true},{"label":"UI Performance","type":"hasLabel","value":true},{"label":"Widget Grouping","type":"hasLabel","value":true},{"label":"Reflow & Resize","type":"hasLabel","value":true},{"label":"Canvas / Grid","type":"hasLabel","value":true},{"label":"Auto Height","type":"hasLabel","value":true},{"label":"Responsive Canvas","type":"hasLabel","value":true},{"label":"Responsive Widget","type":"hasLabel","value":true},{"label":"Responsive Viewport","type":"hasLabel","value":true},{"label":"Spacing","type":"hasLabel","value":true},{"label":"Browser specific","type":"hasLabel","value":true},{"label":"Auto Layout","type":"hasLabel","value":true},{"label":"Fixed layout","type":"hasLabel","value":true},{"label":"Anvil layout","type":"hasLabel","value":true},{"label":"App Navigation","type":"hasLabel","value":true}],"requires":1},"User Education Pod":{"conditions":[{"label":"Documentation","type":"hasLabel","value":true}],"requires":1},"DevOps Pod":{"conditions":[{"label":"Docker","type":"hasLabel","value":true},{"label":"Super Admin","type":"hasLabel","value":true},{"label":"Deployment","type":"hasLabel","value":true},{"label":"K8s","type":"hasLabel","value":true},{"label":"Email Config","type":"hasLabel","value":true},{"label":"Backup & Restore","type":"hasLabel","value":true},{"label":"AWS AMI","type":"hasLabel","value":true},{"label":"Observability","type":"hasLabel","value":true},{"label":"Heroku","type":"hasLabel","value":true},{"label":"New Deployment Mode","type":"hasLabel","value":true},{"label":"Supervisor","type":"hasLabel","value":true},{"label":"Deployment Certificates","type":"hasLabel","value":true},{"label":"Mock Data","type":"hasLabel","value":true},{"label":"AWS ECS","type":"hasLabel","value":true},{"label":"Ingress","type":"hasLabel","value":true},{"label":"Nginx","type":"hasLabel","value":true}],"requires":1},"Design System Pod":{"conditions":[{"label":"Design System Pod","type":"hasLabel","value":true},{"label":"ADS Component Issue","type":"hasLabel","value":true},{"label":"Keyboard accessibility ","type":"hasLabel","value":true},{"label":"Toggle button","type":"hasLabel","value":true},{"label":"ADS Category Token","type":"hasLabel","value":true},{"label":"ADS Component Documentation","type":"hasLabel","value":true},{"label":"ADS Migration","type":"hasLabel","value":true},{"label":"ADS Deduplication ","type":"hasLabel","value":true},{"label":"ADS Revamp","type":"hasLabel","value":true},{"label":"ADS Deduplication","type":"hasLabel","value":true},{"label":"ADS Unit Test","type":"hasLabel","value":true},{"label":"ADS Components","type":"hasLabel","value":true},{"label":"ADS Grayscale","type":"hasLabel","value":true},{"label":"Design System","type":"hasLabel","value":true},{"label":"ADS Typography","type":"hasLabel","value":true},{"label":"ADS Visual Styles","type":"hasLabel","value":true},{"label":"ADS Component Design","type":"hasLabel","value":true},{"label":"Modal Component","type":"hasLabel","value":true}],"requires":1},"Data Platform Pod":{"conditions":[{"label":"Datasource Environments","type":"hasLabel","value":true},{"label":"Datatype issue","type":"hasLabel","value":true},{"label":"Entity Refactor","type":"hasLabel","value":true},{"label":"Core Query Execution","type":"hasLabel","value":true},{"label":"Query Management","type":"hasLabel","value":true},{"label":"Query Settings","type":"hasLabel","value":true},{"label":"SmartSubstitution","type":"hasLabel","value":true},{"label":"Query Generation","type":"hasLabel","value":true},{"label":"Query performance","type":"hasLabel","value":true},{"label":"Suggested Widgets","type":"hasLabel","value":true},{"label":"Page load executions","type":"hasLabel","value":true},{"label":"DSL Update","type":"hasLabel","value":true},{"label":"AST-backend","type":"hasLabel","value":true},{"label":"File upload issues","type":"hasLabel","value":true},{"label":"DocumentDB","type":"hasLabel","value":true},{"label":"Multiple Environments","type":"hasLabel","value":true},{"label":"Platformization","type":"hasLabel","value":true},{"label":"Custom environments","type":"hasLabel","value":true},{"label":"Schema","type":"hasLabel","value":true},{"label":"Secret Management","type":"hasLabel","value":true},{"label":"Publish App","type":"hasLabel","value":true}],"requires":1},"Integrations Pod":{"conditions":[{"label":"New Datasource","type":"hasLabel","value":true},{"label":"Firestore","type":"hasLabel","value":true},{"label":"Google Sheets","type":"hasLabel","value":true},{"label":"Mongo","type":"hasLabel","value":true},{"label":"Redshift","type":"hasLabel","value":true},{"label":"snowflake","type":"hasLabel","value":true},{"label":"S3","type":"hasLabel","value":true},{"label":"Redis","type":"hasLabel","value":true},{"label":"Postgres","type":"hasLabel","value":true},{"label":"GraphQL Plugin","type":"hasLabel","value":true},{"label":"ArangoDB","type":"hasLabel","value":true},{"label":"MsSQL","type":"hasLabel","value":true},{"label":"Elastic Search","type":"hasLabel","value":true},{"label":"OAuth","type":"hasLabel","value":true},{"label":"Airtable","type":"hasLabel","value":true},{"label":"CURL","type":"hasLabel","value":true},{"label":"DynamoDB","type":"hasLabel","value":true},{"label":"Zendesk","type":"hasLabel","value":true},{"label":"Hubspot","type":"hasLabel","value":true},{"label":"Query Forms","type":"hasLabel","value":true},{"label":"Twilio","type":"hasLabel","value":true},{"label":"MySQL","type":"hasLabel","value":true},{"label":"Connection pool","type":"hasLabel","value":true},{"label":"MariaDB","type":"hasLabel","value":true},{"label":"Integrations Pod General","type":"hasLabel","value":true},{"label":"SMTP plugin","type":"hasLabel","value":true},{"label":"Oracle SQL DB","type":"hasLabel","value":true},{"label":"Query filter","type":"hasLabel","value":true},{"label":"Activation - datasources","type":"hasLabel","value":true},{"label":"Onboarding","type":"hasLabel","value":true},{"label":"Generate Page","type":"hasLabel","value":true},{"label":"Sniping Mode","type":"hasLabel","value":true},{"label":"Welcome Screen","type":"hasLabel","value":true},{"label":"Login / Signup","type":"hasLabel","value":true},{"label":"REST API","type":"hasLabel","value":true},{"label":"REST API","type":"hasLabel","value":true},{"label":"Activation - learnability","type":"hasLabel","value":true},{"label":"Datasources","type":"hasLabel","value":true},{"label":"REST API plugin","type":"hasLabel","value":true},{"label":"Prepared statements","type":"hasLabel","value":true}],"requires":1},"Git Pod":{"conditions":[{"label":"Git Version Control","type":"hasLabel","value":true},{"label":"Import-Export-App","type":"hasLabel","value":true},{"label":"Fork App","type":"hasLabel","value":true},{"label":"Git Auto-commit","type":"hasLabel","value":true}],"requires":1},"Mobile Pod":{"conditions":[],"requires":1},"Billing & Usage Pod":{"conditions":[{"label":"CE Instance","type":"hasLabel","value":true},{"label":"Customer Portal","type":"hasLabel","value":true},{"label":"Cloud Services","type":"hasLabel","value":true},{"label":"Billing Integrations","type":"hasLabel","value":true},{"label":"Billing","type":"hasLabel","value":true},{"label":"Self Serve","type":"hasLabel","value":true},{"label":"Enterprise Billing","type":"hasLabel","value":true},{"label":"In-app ramps","type":"hasLabel","value":true},{"label":"Analytics Improvements","type":"hasLabel","value":true},{"label":"Self Serve 1.0","type":"hasLabel","value":true},{"label":"License","type":"hasLabel","value":true},{"label":"Appsmith Business Cloud","type":"hasLabel","value":true},{"label":"BE instance","type":"hasLabel","value":true},{"label":"Embedding Apps","type":"hasLabel","value":true},{"label":"TM_BU","type":"hasLabel","value":true},{"label":"Feature Flagging","type":"hasLabel","value":true},{"label":"Invite flow","type":"hasLabel","value":true},{"label":"Invite users","type":"hasLabel","value":true},{"label":"Home Page","type":"hasLabel","value":true},{"label":"1-click upgrade","type":"hasLabel","value":true}],"requires":1},"Performance Pod":{"conditions":[{"label":"Performance","type":"hasLabel","value":true},{"label":"Performance infra","type":"hasLabel","value":true}],"requires":1},"IDE Pod":{"conditions":[{"label":"Preview mode","type":"hasLabel","value":true},{"label":"IDE Infra","type":"hasLabel","value":true},{"label":"Page Management","type":"hasLabel","value":true}],"requires":1},"Appsmith Labs":{"conditions":[{"label":"AI","type":"hasLabel","value":true},{"label":"Knowledge Retrieval","type":"hasLabel","value":true}],"requires":1},"Workflows Pod":{"conditions":[{"label":"Workflows","type":"hasLabel","value":true}],"requires":1},"Modules pod":{"conditions":[{"label":"Module creator","type":"hasLabel","value":true},{"label":"Module consumer","type":"hasLabel","value":true},{"label":"Package","type":"hasLabel","value":true},{"label":"Package versioning","type":"hasLabel","value":true},{"label":"Convert to module","type":"hasLabel","value":true},{"label":"Query module","type":"hasLabel","value":true},{"label":"JS module","type":"hasLabel","value":true},{"label":"UI module","type":"hasLabel","value":true}],"requires":1},"Templates Pod":{"conditions":[{"label":"Templates","type":"hasLabel","value":true},{"label":"Partial-import-export","type":"hasLabel","value":true},{"label":"Building blocks","type":"hasLabel","value":true}],"requires":1},"QA Pod":{"conditions":[{"label":"QA","type":"hasLabel","value":true},{"label":"Automation Test","type":"hasLabel","value":true},{"label":"TestGap","type":"hasLabel","value":true},{"label":"Automation failures","type":"hasLabel","value":true},{"label":"Needs automation","type":"hasLabel","value":true}],"requires":1},"Widget design system POD":{"conditions":[{"label":"App Theming","type":"hasLabel","value":true},{"label":"Widget Styling","type":"hasLabel","value":true},{"label":"Checkbox Component","type":"hasLabel","value":true},{"label":"WDS team","type":"hasLabel","value":true},{"label":"Widget design system POD","type":"hasLabel","value":true}],"requires":1}}},"root":"."}],"labels":{"Tab Widget":{"color":"e2c76c","name":"Tab Widget","description":""},"Dont merge":{"color":"ADB39C","name":"Dont merge","description":""},"Epic":{"color":"3E4B9E","name":"Epic","description":"A zenhub epic that describes a project"},"Menu Button Widget":{"color":"235708","name":"Menu Button Widget","description":"Issues related to Menu Button widget"},"Checkbox Group widget":{"color":"bbeecd","name":"Checkbox Group widget","description":"Issues related to Checkbox Group Widget"},"Input Widget":{"color":"ae65d8","name":"Input Widget","description":""},"Security":{"color":"99139C","name":"Security","description":""},"QA":{"color":"","name":"QA","description":"Needs QA attention"},"Verified":{"color":"9bf416","name":"Verified","description":""},"Wont Fix":{"color":"ffffff","name":"Wont Fix","description":"This will not be worked on"},"MySQL":{"color":"c9ddc6","name":"MySQL","description":"Issues related to MySQL plugin"},"Development":{"color":"9F8A02","name":"Development","description":""},"Help Wanted":{"color":"008672","name":"Help Wanted","description":"Extra attention is needed"},"Home Page":{"color":"9c0c8e","name":"Home Page","description":"Issues related to the application home page"},"Rating Widget":{"color":"235708","name":"Rating Widget","description":"Issues related to the rating widget"},"Stat Box Widget":{"color":"f1c9ce","name":"Stat Box Widget","description":"Issues related to stat box"},"Enhancement":{"color":"a2eeef","name":"Enhancement","description":"New feature or request"},"Fork App":{"color":"30c76d","name":"Fork App","description":"Issues related to forking apps"},"Container Widget":{"color":"19AD0D","name":"Container Widget","description":"Container widget"},"Papercut":{"color":"B562F6","name":"Papercut","description":""},"Needs Design":{"color":"bfd4f2","name":"Needs Design","description":"needs design or changes to design"},"i18n":{"color":"1799b0","name":"i18n","description":"Represents issues that need to be tackled to handle internationalization"},"Rich Text Editor Widget":{"color":"f72cac","name":"Rich Text Editor Widget","description":""},"Onboarding":{"color":"30c76d","name":"Onboarding","description":"Issues related to onboarding new developers"},"skip-changelog":{"color":"06086F","name":"skip-changelog","description":"Adding this label to a PR prevents it from being listed in the changelog"},"Low":{"color":"79e53b","name":"Low","description":"An issue that is neither critical nor breaks a user flow"},"potential-duplicate":{"color":"d3cb2e","name":"potential-duplicate","description":"This label marks issues that are potential duplicates of already open issues"},"Audio Widget":{"color":"447B9A","name":"Audio Widget","description":"Issues related to Audio Widget"},"Firestore":{"color":"8078b0","name":"Firestore","description":"Issues related to the firestore Integration"},"New Widget":{"color":"be4cf2","name":"New Widget","description":"A request for a new widget"},"Modal Widget":{"color":"03846f","name":"Modal Widget","description":""},"UX Improvement":{"color":"f4a089","name":"UX Improvement","description":""},"S3":{"color":"8078b0","name":"S3","description":"Issues related to the S3 plugin"},"Release Blocker":{"color":"5756bf","name":"Release Blocker","description":"This issue must be resolved before the release"},"safari":{"color":"51C6AA","name":"safari","description":"Bugs seen on safari browser"},"Example Apps":{"color":"1799b0","name":"Example Apps","description":"Example apps created for new signups"},"MultiSelect Widget":{"color":"AB62D4","name":"MultiSelect Widget","description":"Issues related to MultiSelect Widget"},"Widget Styling":{"color":"905420","name":"Widget Styling","description":"all about widget styling"},"Calendar Widget":{"color":"8c6644","name":"Calendar Widget","description":""},"Website":{"color":"151720","name":"Website","description":"Related to www.appsmith.com website"},"Low effort":{"color":"8B59F0","name":"Low effort","description":"Something that'll take a few days to build"},"App Viewers Pod":{"color":"cd8ef9","name":"App Viewers Pod","description":"This label assigns issues to the app viewers pod"},"Checkbox Widget":{"color":"bbeecd","name":"Checkbox Widget","description":""},"Spam":{"color":"620faf","name":"Spam","description":""},"Voice Recorder Widget":{"color":"85bc87","name":"Voice Recorder Widget","description":""},"Select Widget":{"color":"0c669e","name":"Select Widget","description":"Select or dropdown widget"},"Bug":{"color":"8ba6fd","name":"Bug","description":"Something isn't right"},"Widget Validation":{"color":"6990BC","name":"Widget Validation","description":"Issues related to widget property validation"},"Generate Page":{"color":"30c76d","name":"Generate Page","description":"Issures related to page generation"},"File Picker Widget":{"color":"6ae4f2","name":"File Picker Widget","description":""},"snowflake":{"color":"8078b0","name":"snowflake","description":"Issues related to the snowflake Integration"},"Automation":{"color":"CCAF60","name":"Automation","description":""},"hotfix":{"color":"BA3F1D","name":"hotfix","description":""},"Team Managers Pod":{"color":"bddb81","name":"Team Managers Pod","description":"Issues that team managers care about for the security and efficiency of their teams"},"Import-Export-App":{"color":"15076d","name":"Import-Export-App","description":"Issues related to importing and exporting apps"},"High effort":{"color":"A7E87B","name":"High effort","description":"Something that'll take more than a month to build"},"Telemetry":{"color":"bc70f9","name":"Telemetry","description":"Issues related to instrumenting appsmith"},"Radio Widget":{"color":"91ef15","name":"Radio Widget","description":""},"Omnibar":{"color":"10b5ce","name":"Omnibar","description":"Issues related to the omnibar for navigation"},"Button Widget":{"color":"34efae","name":"Button Widget","description":""},"Switch widget":{"color":"33A8CE","name":"Switch widget","description":"The switch widget"},"Map Widget":{"color":"7eef7a","name":"Map Widget","description":""},"Task":{"color":"085630","name":"Task","description":"A simple Todo"},"Design System":{"color":"2958a4","name":"Design System","description":"Design system"},"opera":{"color":"C63F5B","name":"opera","description":"Any issues identified on the opera browser"},"Login / Signup":{"color":"30c76d","name":"Login / Signup","description":"Authentication flows"},"Image Widget":{"color":"8de8ad","name":"Image Widget","description":""},"firefox":{"color":"6d56e2","name":"firefox","description":""},"Property Pane":{"color":"b356ff","name":"Property Pane","description":"Issues related to the behaviour of the property pane"},"Deployment":{"color":"93491f","name":"Deployment","description":"Installation process of appsmith"},"IDE":{"color":"61b2ee","name":"IDE","description":"Issues related to the IDE"},"Production":{"color":"b60205","name":"Production","description":""},"Dependencies":{"color":"0366d6","name":"Dependencies","description":"Pull requests that update a dependency file"},"Google Sheets":{"color":"8078b0","name":"Google Sheets","description":"Issues related to Google Sheets"},"Icon Button Widget":{"color":"D319CE","name":"Icon Button Widget","description":"Issues related to the icon button widget"},"Mongo":{"color":"8078b0","name":"Mongo","description":"Issues related to Mongo DB plugin"},"Documentation":{"color":"a8dff7","name":"Documentation","description":"Improvements or additions to documentation"},"TestGap":{"color":"","name":"TestGap","description":"Issues identified for test plan improvement"},"keyboard shortcut":{"color":"0688B6","name":"keyboard shortcut","description":""},"Git Version Control":{"color":"858172","name":"Git Version Control","description":"Issues related to version control"},"Reopen":{"color":"897548","name":"Reopen","description":""},"Redshift":{"color":"8078b0","name":"Redshift","description":"Issues related to the redshift integration"},"Date Picker Widget":{"color":"ef1ce1","name":"Date Picker Widget","description":""},"Entity Explorer":{"color":"a2e2f9","name":"Entity Explorer","description":"Issues related to navigation using the entity explorer"},"JS Linting & Errors":{"color":"E56AA5","name":"JS Linting & Errors","description":"Issues related to JS Linting and errors"},"iFrame":{"color":"3CD1DB","name":"iFrame","description":"Issues related to iFrame"},"Stale":{"color":"ededed","name":"Stale","description":null},"Debugger":{"color":"e79062","name":"Debugger","description":"Issues related to the debugger"},"Quick effort":{"color":"95ED65","name":"Quick effort","description":"Something that'll take a few hours to build"},"Text Widget":{"color":"d130d1","name":"Text Widget","description":""},"Video Widget":{"color":"23dd4b","name":"Video Widget","description":""},"Datasources":{"color":"3d590f","name":"Datasources","description":"Issues related to configuring datasource on appsmith"},"error":{"color":"B66773","name":"error","description":"All issues connected to error messages"},"Form Widget":{"color":"09ed77","name":"Form Widget","description":""},"Needs Triaging":{"color":"e8b851","name":"Needs Triaging","description":"Needs attention from maintainers to triage"},"Autocomplete":{"color":"235708","name":"Autocomplete","description":"Issues related to the autocomplete"},"hacktoberfest":{"color":"0052cc","name":"hacktoberfest","description":"All issues that can be solved by the community during Hacktoberfest"},"Medium effort":{"color":"D31156","name":"Medium effort","description":"Something that'll take more than a week but less than a month to build"},"Release":{"color":"57e5e0","name":"Release","description":""},"High":{"color":"c94d14","name":"High","description":"This issue blocks a user from building or impacts a lot of users"},"UI Performance":{"color":"1799b0","name":"UI Performance","description":"Issues related to UI performance"},"UI Builders Pod":{"color":"517fba","name":"UI Builders Pod","description":"Issues that UI Builders face using appsmith"},"Deploy Preview":{"color":"bfdadc","name":"Deploy Preview","description":"Issues found in Deploy Preview"},"Needs Tests":{"color":"8ee263","name":"Needs Tests","description":"Needs automated tests to assert a feature/bug fix"},"Refactor":{"color":"B96662","name":"Refactor","description":"needs refactoring of code"},"Divider Widget":{"color":"235708","name":"Divider Widget","description":"Issues related to the divider widget"},"Table Widget":{"color":"2eead1","name":"Table Widget","description":""},"Needs More Info":{"color":"e54c10","name":"Needs More Info","description":"Needs additional information"},"Good First Issue":{"color":"7057ff","name":"Good First Issue","description":"Good for newcomers"},"UI Improvement":{"color":"9aeef4","name":"UI Improvement","description":""},"Backend":{"color":"d4c5f9","name":"Backend","description":"This marks the issue or pull request to reference server code"},"Frontend":{"color":"87c7f2","name":"Frontend","description":"This label marks the issue or pull request to reference client code"},"In App Comms":{"name":"In App Comms","description":"Issues around communication with appsmith instances","color":"463cca"},"Chart Widget":{"color":"616ecc","name":"Chart Widget","description":""},"List Widget":{"color":"8508A0","name":"List Widget","description":"Issues related to the list widget"},"Duplicate":{"color":"cfd3d7","name":"Duplicate","description":"This issue or pull request already exists"},"JS Snippets":{"color":"8d62d2","name":"JS Snippets","description":"issues related to JS Snippets"},"Copy Paste":{"name":"Copy Paste","description":"Issues related to copy paste","color":"b4f0a9"},"Drag & Drop":{"name":"Drag & Drop","description":"Issues related to the drag & drop experience","color":"92115a"},"BE Coders Pod":{"color":"5d9848","name":"BE Coders Pod","description":"Issues related to users writing code to fetch and update data"},"FE Coders Pod":{"color":"a7effc","name":"FE Coders Pod","description":"Issues related to users writing javascript in appsmith"},"New Developers Pod":{"color":"6310da","name":"New Developers Pod","description":"Issues that new developers face while exploring the IDE"},"Sniping Mode":{"name":"Sniping Mode","description":"Issues related to sniping mode","color":"30c76d"},"Redis":{"name":"Redis","description":"Issues related to Redis","color":"8078b0"},"New Datasource":{"color":"60b14c","name":"New Datasource","description":"Requests for new datasources"},"Evaluated Value":{"name":"Evaluated Value","description":"Issues related to evaluated values","color":"39f6e7"},"Undo/Redo":{"name":"Undo/Redo","description":"Issues related to undo/redo","color":"f25880"},"App Navigation":{"name":"App Navigation","description":"Issues related to the topbar navigation and configuring it","color":"4773ab"},"Responsive Viewport":{"color":"d12d2e","name":"Responsive Viewport","description":"Issues seen on different viewports like mobile"},"Widgets Pane":{"name":"Widgets Pane","description":"Issues related to the discovery and organisation of widgets","color":"ad5d78"},"View Mode":{"color":"1799b0","name":"View Mode","description":"Issues related to the view mode"},"User Education Pod":{"name":"User Education Pod","description":"Issues related to user education","color":"1799b0"},"Content":{"name":"Content","description":"For content related topics i.e blogs, templates, videos","color":"a8dff7"},"Embedding Apps":{"name":"Embedding Apps","description":"Issues related to embedding","color":"30c76d"},"Slash Command":{"name":"Slash Command","description":"Issues related to the slash command","color":"a0608e"},"Widget Property":{"name":"Widget Property","description":"Issues related to adding / modifying widget properties across widgets","color":"5e92cb"},"Windows":{"name":"Windows","description":"Issues related exclusively to Windows systems","color":"b4cb8a"},"Old App Issues":{"name":"Old App Issues","description":"Issues related to apps old apps a few weeks old and app issues in stale browser session","color":"87ab18"},"Document Viewer Widget":{"name":"Document Viewer Widget","description":"Issues related to Document Viewer Widget","color":"899d4b"},"Radio Group Widget":{"name":"Radio Group Widget","description":"Issues related to radio group widget","color":"b68495"},"Super Admin":{"name":"Super Admin","description":"Issues related to the super admin page","color":"aa95cf"},"Postgres":{"name":"Postgres","description":"Postgres related issues","color":"8078b0"},"New JS Function":{"name":"New JS Function","description":"Issues related to adding a JS Function","color":"8e8aa4"},"Cannot Reproduce Issue":{"color":"93c9cc","name":"Cannot Reproduce Issue","description":"Issues that cannot be reproduced"},"Widget Grouping":{"name":"Widget Grouping","description":"Issues related to Widget Grouping","color":"a49951"},"K8s":{"name":"K8s","description":"Kubernetes related issues","color":"5f318a"},"Docker":{"name":"Docker","description":"Issues related to docker","color":"89b808"},"Camera Widget":{"name":"Camera Widget","description":"Issues and enhancements related to camera widget","color":"e6038e"},"SAAS Plugins":{"name":"SAAS Plugins","description":"Issues related to SAAS Plugins","color":"ef9c9d"},"JS Promises":{"name":"JS Promises","description":"Issues related to promises","color":"d7771f"},"OnPageLoad":{"name":"OnPageLoad","description":"OnPageLoad issues on functions and queries","color":"50559d"},"JS Usability":{"name":"JS Usability","description":"usability issues with JS editor and JS elsewhere","color":"a302b0"},"Currency Input Widget":{"name":"Currency Input Widget","description":"Issues related to currency input widget","color":"b2164f"},"TreeSelect":{"name":"TreeSelect","description":"Issues related to TreeSelect Widget","color":"a1633e"},"MultiTree Select Widget":{"name":"MultiTree Select Widget","description":"Issues related to MultiTree Select Widget","color":"a1633e"},"Welcome Screen":{"name":"Welcome Screen","description":"Issues related to the welcome screen","color":"30c76d"},"Realtime Commenting":{"color":"a70b86","name":"Realtime Commenting","description":"In-app communication between teams"},"Phone Input Widget":{"name":"Phone Input Widget","description":"Issues related to the Phone Input widget","color":"a70b86"},"JSON Form":{"name":"JSON Form","description":"Issue / features related to the JSON form wiget","color":"46b209"},"All Widgets":{"name":"All Widgets","description":"Issues related to all widgets","color":"972b36"},"V1":{"name":"V1","description":"V1","color":"67ab2e"},"Reflow & Resize":{"name":"Reflow & Resize","description":"All issues related to reflow and resize experience","color":"748a13"},"App Theming":{"name":"App Theming","description":"Items that are related to the App level theming controls epic","color":"905420"},"SSO":{"name":"SSO","description":"Issues, requests and enhancements around Single sign-on.","color":"bf019b"},"Multi User Realtime":{"name":"Multi User Realtime","description":"Issues related to multiple users using or editing an application","color":"e7b6ce"},"Templates":{"name":"Templates","description":"Issues related to templates","color":"b893f6"},"Ready for design":{"name":"Ready for design","description":"this issue is ready for design: it contains clear problem statements and other required information","color":"ebf442"},"Support":{"name":"Support","description":"Issues created by the A-force team to address user queries","color":"1740f3"},"Button Group widget":{"name":"Button Group widget","description":"Issue and enhancements related to the button group widget","color":"f17025"},"GraphQL Plugin":{"name":"GraphQL Plugin","description":"Issues related to GraphQL plugin","color":"8078b0"},"DevOps Pod":{"name":"DevOps Pod","description":"Issues related to devops","color":"d956c7"},"medium":{"name":"medium","description":"Issues that frustrate users due to poor UX","color":"23dfd9"},"ArangoDB":{"name":"ArangoDB","description":"Issues related to arangoDB","color":"8078b0"},"Code Refactoring":{"name":"Code Refactoring","description":"Issues related to code refactoring","color":"76310e"},"Progress bar widget":{"name":"Progress bar widget","description":"To track issues related to progress bar","color":"2d7abf"},"Audio Recorder Widget":{"name":"Audio Recorder Widget","description":"Issues related to Audio Recorder Widget","color":"9accef"},"Airtable":{"name":"Airtable","description":"Issues for Airtable","color":"60885f"},"RBAC":{"name":"RBAC","description":"Issues, requests and enhancements around RBAC.","color":"9211c3"},"Canvas / Grid":{"name":"Canvas / Grid","description":"Issues related to the canvas","color":"16b092"},"Email Config":{"name":"Email Config","description":"Issues related to configuring the email service","color":"2a21d1"},"CURL":{"name":"CURL","description":"Issues related to CURL impor","color":"60885f"},"Canvas Zooms":{"name":"Canvas Zooms","description":"Issues related to zooming the canvas","color":"e6038e"},"business":{"name":"business","description":"Features that will be a part of our business edition","color":"cd59eb"},"Action Pod":{"name":"Action Pod","description":"","color":"ee2e36"},"AutomationGap1":{"color":"a5e07c","name":"AutomationGap1","description":"Issues that needs automated tests"},"A-Force11":{"name":"A-Force11","description":"Issues raised by A-Force team","color":"d667b6"},"Business Edition":{"name":"Business Edition","description":"Features that will be a part of our business edition","color":"89bb6c"},"storeValue":{"name":"storeValue","description":"Issues related to the store value function","color":"5d3e66"},"DynamoDB":{"name":"DynamoDB","description":"Issues that are related to DynamoDB should have this label","color":"60885f"},"Design System Pod":{"name":"Design System Pod","description":"Appsmith design system related issues","color":"706f03"},"ABAC":{"color":"e009a5","name":"ABAC","description":"User permissions and access controls"},"Backup & Restore":{"name":"Backup & Restore","description":"Issues related to backup and restore","color":"86874d"},"Billing":{"name":"Billing","description":"Billing infrastructure and flows for Business Edition and Trial users","color":"d2bc40"},"Datatype issue":{"name":"Datatype issue","description":"Issues that have risen because data types weren't handled","color":"60885f"},"OAuth":{"name":"OAuth","description":"OAuth related bugs or features","color":"60885f"},"Table Widget V2":{"name":"Table Widget V2","description":"Issues related to Table Widget V2","color":"3a7192"},"IDE Navigation":{"name":"IDE Navigation","description":"Issues/feature requests related to IDE navigation, and context switching","color":"bc0cba"},"Query performance":{"name":"Query performance","description":"Issues that have to do with lack in performance of query execution","color":"e4d966"},"SAAS Manager App":{"name":"SAAS Manager App","description":"Issues with the SAAS manager app","color":"d427db"},"Twilio":{"name":"Twilio","description":"Issues related to Twilio integration","color":"23ba8d"},"Hubspot":{"name":"Hubspot","description":"Issues related to Hubspot integration","color":"60885f"},"Zendesk":{"name":"Zendesk","description":"Issues related to Zendesk integration","color":"60885f"},"Entity Refactor":{"name":"Entity Refactor","description":"Issues related to refactor logic","color":"418fa4"},"Branding":{"name":"Branding","description":"All issues under branding and whitelabelling appsmith ecosystem","color":"7aaaf1"},"Map Chart Widget":{"name":"Map Chart Widget","description":"Issues related to Map Chart Widgets","color":"c8397f"},"Product Catchup":{"name":"Product Catchup","description":"Issues created in the product catchup","color":"29cd2c"},"Framework Functions":{"name":"Framework Functions","description":"Issues related to internal functions like showAlert(), navigateTo() etc...","color":"c25a09"},"Frontend Libraries Upgrade":{"name":"Frontend Libraries Upgrade","description":"Issues related to frontend libraries upgrade","color":"ede1fc"},"Audit Logs":{"name":"Audit Logs","description":"Audit trails to ensure data security","color":"f3fd62"},"MsSQL":{"name":"MsSQL","description":"Issues related to MsSQL plugin","color":"8078b0"},"Data Platform Pod":{"name":"Data Platform Pod","description":"Issues related to the underlying data platform","color":"3f8c3a"},"Integrations Pod":{"name":"Integrations Pod","description":"Issues related to a specific integration","color":"5dbbb1"},"Datasource Environments":{"name":"Datasource Environments","description":"Issues related to datasource environments","color":"bb7a14"},"Elastic Search":{"name":"Elastic Search","description":"Issues related to the elastic search datasource","color":"8078b0"},"Core Query Execution":{"color":"418fa4","name":"Core Query Execution","description":"Issues related to the execution of all queries"},"Query Management":{"name":"Query Management","description":"Issues related to the CRUD of actions or queries","color":"6a5b42"},"Query Settings":{"name":"Query Settings","description":"Issues related to the settings of all queries","color":"c7da7a"},"Code Editor":{"name":"Code Editor","description":"Issues related to the code editor","color":"4ca16e"},"Query Forms":{"color":"12b253","name":"Query Forms","description":"Isuses related to the query forms"},"JS Objects":{"color":"22962c","name":"JS Objects","description":"Issues related to JS Objects"},"JS Evaluation":{"color":"22962c","name":"JS Evaluation","description":"Issues related to JS evaluation on the platform"},"SmartSubstitution":{"name":"SmartSubstitution","description":"Issues related to Smart substitution of mustache bindings in queries","color":"e4d966"},"Query Generation":{"name":"Query Generation","description":"Issues related to query generation","color":"e4d966"},"Suggested Widgets":{"name":"Suggested Widgets","description":"Issues related to suggesting widgets based on query response","color":"e4d966"},"Page load executions":{"name":"Page load executions","description":"Issues related to page load execution","color":"5696b2"},"Code Scanner Widget":{"name":"Code Scanner Widget","description":"Issues related to code scanner widget","color":"9bc1a0"},"Clean URLs":{"name":"Clean URLs","description":"Issues related to clean URLs epic","color":"112623"},"Widget keyboard accessibility":{"name":"Widget keyboard accessibility","description":"All issues related to keyboard accessibility in widgets","color":"b626fd"},"Connection pool":{"name":"Connection pool","description":"issues to do with connection pooling of various plugins","color":"94fe36"},"List Widget V2":{"name":"List Widget V2","description":"Issues related to the list widget v2","color":"adaaf7"},"Auto Height":{"name":"Auto Height","description":"Issues related to dynamic height of widgets","color":"5149cf"},"cypress_failed_test":{"name":"cypress_failed_test","description":"Cypress failed tests","color":"4745d5"},"Needs validation":{"name":"Needs validation","description":"Needs problem validation before being picked up","color":"66673d"},"Slider Widget":{"name":"Slider Widget","description":"Issues raised for slider widgets.","color":"2eef5f"},"Multitenancy":{"name":"Multitenancy","description":"Support multitenancy within single appsmith instance","color":"8c49a9"},"Git Pod":{"name":"Git Pod","description":"Anything related to git sync","color":"2e5ba4"},"Mobile Pod":{"name":"Mobile Pod","description":"All issues related to mobile responsiveness","color":"6c97fd"},"Responsive Widget":{"name":"Responsive Widget","description":"All issues related to widget responsiveness","color":"d12d2e"},"Responsive Canvas":{"name":"Responsive Canvas","description":"All issues related to canvas responsiveness","color":"45a0a8"},"Conversion Algorithm":{"name":"Conversion Algorithm","description":"All issue related to converting app from fixed to flex mode & vice versa","color":"d12d2e"},"Spacing":{"name":"Spacing","description":"All issue related to spacing between widgets in auto layout","color":"d12d2e"},"Browser specific":{"name":"Browser specific","description":"All issue related to browser","color":"d12d2e"},"Error Handling":{"name":"Error Handling","description":"Issues related to error handling","color":"4e1872"},"Performance infra":{"name":"Performance infra","description":"all issue related to the performance infra","color":"8a60f6"},"DSL Update":{"name":"DSL Update","description":"Issues related to storing and updating the DSL","color":"e16cf3"},"AST-frontend":{"name":"AST-frontend","description":"Issues related to maintaining AST logic","color":"434a3a"},"AST-backend":{"name":"AST-backend","description":"Backend issues related to AST parsing","color":"c476eb"},"MariaDB":{"name":"MariaDB","description":"MariaDB datasource","color":"8428c3"},"Billing & Usage Pod":{"name":"Billing & Usage Pod","description":"Issues pertaining to licensing, billing, usage across self serve and enterprise customers","color":"256808"},"ADS Component Issue":{"name":"ADS Component Issue","description":"Issues which are caused due to ADS components","color":"d89119"},"Regressed":{"color":"723fd0","name":"Regressed","description":"Scenarios that were working before but have now regressed"},"Needs RCA":{"name":"Needs RCA","description":"a critical or high priority issue that needs an RCA","color":"2cc68f"},"Custom JS Libraries":{"name":"Custom JS Libraries","description":"Issues related to adding custom JS library","color":"bacb6d"},"Integrations Pod General":{"name":"Integrations Pod General","description":"Issues related to the Integrations Pod that don't fit into other tags.","color":"287823"},"Performance Pod":{"name":"Performance Pod","description":"All things related to Appsmith performance","color":"b5a25d"},"Performance":{"name":"Performance","description":"Issues related to performance","color":"9a18d7"},"File upload issues":{"name":"File upload issues","description":"Issues related to uploading any type of files from within Appsmith","color":"8154df"},"Action Selector":{"name":"Action Selector","description":"Issues related to action selector on the property pane","color":"2f9e20"},"Community Reported":{"name":"Community Reported","description":"issues reported by community members","color":"1402e5"},"JS Function execution":{"name":"JS Function execution","description":"JS function execution","color":"7c2de1"},"Self Serve":{"name":"Self Serve","description":"For all issues related to self-serve flow for business edition","color":"4dacfc"},"Self Serve 1.0":{"name":"Self Serve 1.0","description":"For all issues related to v1 of the self serve project","color":"ae839e"},"CE Instance":{"name":"CE Instance","description":"For all issues relating to usage, licensing or billing on the CE instance","color":"d2bc40"},"Customer Portal":{"name":"Customer Portal","description":"For all tasks/issues pertaining to customer.appsmith.com","color":"d2bc40"},"Cloud Services":{"name":"Cloud Services","description":"For all tasks/issues on Appsmith cloud-services relating to licensing, usage and billing","color":"d2bc40"},"Billing Integrations":{"name":"Billing Integrations","description":"For all issues relating to 3P integrations Appsmith is using for billing & usage","color":"d2bc40"},"One-click Binding":{"name":"One-click Binding","description":"Issues related to the One click binding epic","color":"f1661c"},"Airgap":{"name":"Airgap","description":"Tickets related to supporting air-gapped Appsmith instances","color":"1cb294"},"SMTP plugin":{"name":"SMTP plugin","description":"Issues related to SMTP plugin","color":"541457"},"AWS AMI":{"name":"AWS AMI","description":"Issues Related to AWS AMI","color":"b44680"},"Old widget version":{"name":"Old widget version","description":"Use this label to raise issue specific only to an older version of a widget","color":"ff3814"},"Enterprise Billing":{"name":"Enterprise Billing","description":"To track all tasks/issues related to licensing & billing for enterprise customers","color":"14c156"},"Appsmith Business Cloud":{"name":"Appsmith Business Cloud","description":"Issues related to our business cloud offering","color":"89bb6c"},"Oracle SQL DB":{"name":"Oracle SQL DB","description":"Issues related to the Oracle plugin","color":"cbabcb"},"Community Contributor":{"name":"Community Contributor","description":"Meant to track issues that are assigned to external contributors","color":"149ab6"},"widget vertical alignment":{"name":"widget vertical alignment","description":"All issue related widget vertical alignment on the auto layout canvas","color":"d12d2e"},"Observability":{"name":"Observability","description":"Issues related to observability on the Appsmith instance","color":"dff913"},"Checkbox Component":{"name":"Checkbox Component","description":"This labels deals with checkbox component in wds package","color":"75a401"},"In-app ramps":{"name":"In-app ramps","description":"For all tasks/issues relating to adding in-app ramps in the community edition of the product","color":"8abae0"},"Analytics Improvements":{"name":"Analytics Improvements","description":"For all tasks focused on improving our overall analytics and fixing any issues ","color":"29b8ed"},"WDS team":{"name":"WDS team","description":"","color":"8d675a"},"Enterprise Edition":{"name":"Enterprise Edition","description":"Features that will be supported in Enterprise Edition only","color":"984f5e"},"Query filter":{"name":"Query filter","description":"Issues related to query filtering, e.g., WHERE clause","color":"a15134"},"Keyboard accessibility ":{"name":"Keyboard accessibility ","description":"All issue related to ADS component keyboard accessibility","color":"2ba696"},"Toggle button":{"name":"Toggle button","description":"All issue related to ADS toggle button","color":"edc47f"},"Feature Flagging":{"name":"Feature Flagging","description":"Anything related feature flagging","color":"8d8a09"},"SCIM":{"name":"SCIM","description":"Label to collate our SCIM issues","color":"61a852"},"ADS Category Token":{"name":"ADS Category Token","description":"All issues related appsmith design system category tokens","color":"920961"},"ADS Component Documentation":{"name":"ADS Component Documentation","description":"All issues Appsmith design system component documentation","color":"64c46a"},"ADS Migration":{"name":"ADS Migration","description":"All issues related to Appsmith design system migration","color":"b082d6"},"ADS Deduplication ":{"name":"ADS Deduplication ","description":"Replacing component with ADS components","color":"b082d6"},"ADS Revamp":{"name":"ADS Revamp","description":"All issues related to ads revamp. ","color":"b082d6"},"ADS Deduplication":{"name":"ADS Deduplication","description":"Replacing component with ADS components","color":"b082d6"},"ADS Grayscale":{"name":"ADS Grayscale","description":"Support grayscale color changes","color":"b03577"},"ADS Unit Test":{"name":"ADS Unit Test","description":"All issue related ads unit cases ","color":"b082d6"},"ADS Components":{"name":"ADS Components","description":"All issues related ADS components","color":"b082d6"},"Widget Discoverability":{"name":"Widget Discoverability","description":"Issues related to Widget Discoverability","color":"7b55ce"},"Widget setter method":{"name":"Widget setter method","description":"Issues with widget property setters","color":"8dce87"},"License":{"name":"License","description":"For all issues/tasks related to licensing of appsmith-ee edition","color":"90ee98"},"DocumentDB":{"name":"DocumentDB","description":"Issues related to support DocumentDB in Appsmith Data layer","color":"2c8b56"},"Multiple Environments":{"name":"Multiple Environments","description":"Issues or tasks related to multiple environments","color":"4e972b"},"Platformization":{"name":"Platformization","description":"Issues or tasks related to platformization of Appsmith codebase","color":"4e972b"},"Activation - datasources":{"name":"Activation - datasources","description":"issues related to activation projects","color":"7c7ace"},"Partial-import-export":{"name":"Partial-import-export","description":"Label for granular reusability.","color":"717732"},"AI":{"name":"AI","description":"All tasks related to AI","color":"75c4ce"},"Custom environments":{"name":"Custom environments","description":"Issues with creating or working with custom environments","color":"2137d6"},"ADS Typography":{"name":"ADS Typography","description":"All issue related typographical changes","color":"2dbe8d"},"Auto Layout":{"name":"Auto Layout","description":"Issues relates to auto layout","color":"92cf8c"},"Heroku":{"name":"Heroku","description":"Issues related to Heroku","color":"a81b69"},"ADS Visual Styles":{"name":"ADS Visual Styles","description":"All issues related to ADS visual styles","color":"d3da89"},"ADS Component Design":{"name":"ADS Component Design","description":"All issue related to component design","color":"5cc91e"},"Modal Component":{"name":"Modal Component","description":"All issue related to ads modal component","color":"ee63f3"},"App setting":{"name":"App setting","description":"Related to app settings panel within the app","color":"144206"},"BE instance":{"name":"BE instance","description":"For all issues related to license, billing on BE instance","color":"ae8f98"},"Schema":{"name":"Schema","description":"Issues related to database schema","color":"c470c2"},"Fixed layout":{"name":"Fixed layout","description":"issues related to fixed layout","color":"b66681"},"Anvil layout":{"name":"Anvil layout","description":"issues related to the new layout system anvil","color":"722bf0"},"New Deployment Mode":{"name":"New Deployment Mode","description":"Support a new mode of deployment","color":"108033"},"Custom widgets":{"name":"Custom widgets","description":"For all issues related to the custom widget project","color":"c9db9c"},"IDE Pod":{"name":"IDE Pod","description":"https://app.zenhub.com/workspaces/new-developers-pod-60507ad1d4b98d00150a2858/board","color":"d3d248"},"TM_BU":{"name":"TM_BU","description":"The issues on Team Manager which needs to be taken up by Billing & Usage","color":"198cdf"},"Homepage Experience V2":{"name":"Homepage Experience V2","description":"Label for reporting new tasks and bug fixes related to revamped homepage experience","color":"c55d54"},"Appsmith Labs":{"name":"Appsmith Labs","description":"All things related to AI and other new initiatives ","color":"712d51"},"Customer Success":{"name":"Customer Success","description":"Issues that the success team cares about","color":"6ccabd"},"Invite flow":{"name":"Invite flow","description":"Invite users flow and any associated actions","color":"881b35"},"Invite users":{"name":"Invite users","description":"Invite users flow and any associated actions","color":"23e6d6"},"Workflows Pod":{"name":"Workflows Pod","description":"For all issues related to the Workflows feature","color":"a86802"},"DailyPromotionBlocker":{"name":"DailyPromotionBlocker","description":"DailyPromotion Blocker","color":"9b2280"},"JS Binding":{"name":"JS Binding","description":"All issues related to the JS Binding experience","color":"422fed"},"Knowledge Retrieval":{"name":"Knowledge Retrieval","description":"All issues related to knowledge retrieval on Appsmith AI","color":"a36890"},"REST API":{"name":"REST API","description":"REST API plugin related issues","color":"e3ede5"},"1-click upgrade":{"name":"1-click upgrade","description":"For all issues/tasks related to 1-click upgrade & downgrade project","color":"51b5ff"},"Activation - learnability":{"name":"Activation - learnability","description":"Activation - learnability","color":"96fc76"},"Critical":{"color":"a1e3db","name":"Critical","description":"This issue breaks existing apps. Drop everything else to resolve"},"Modules pod":{"name":"Modules pod","description":"issues that belong to the modules pod","color":"4c6329"},"Module creator":{"name":"Module creator","description":"Issues related to the module creator side","color":"bb2c05"},"Module consumer":{"name":"Module consumer","description":"Issues related to the module consumer side","color":"83d3c5"},"Package":{"name":"Package","description":"Issues related to packages","color":"2ad485"},"Package versioning":{"name":"Package versioning","description":"ISsues related to how we manage versions for packages","color":"4c5218"},"Convert to module":{"name":"Convert to module","description":"Issues related to the module creation flow using conversion","color":"4c5218"},"Query module":{"name":"Query module","description":"Issues affecting query modules or its instances","color":"b11a7e"},"JS module":{"name":"JS module","description":"Issues affecting JS modules or its instances","color":"bf76f6"},"Templates Pod":{"name":"Templates Pod","description":"Issues related to Templates","color":"e7b3b9"},"Secret Management":{"name":"Secret Management","description":"Issues related to secret management","color":"cce8e7"},"REST API plugin":{"name":"REST API plugin","description":"REST API plugin related issues","color":"b5948a"},"UI module":{"name":"UI module","description":"Issues affecting UI modules or its instances","color":"d2acee"},"Preview mode":{"name":"Preview mode","description":"Issues related to app previews","color":"3fb8f2"},"Git Auto-commit":{"name":"Git Auto-commit","description":"Issues related to autocommit","color":"717732"},"QA Pod":{"name":"QA Pod","description":"Issues under the QA Pod","color":"717732"},"Automation Test":{"name":"Automation Test","description":"","color":""},"Automation failures":{"name":"Automation failures","description":"","color":""},"Needs automation":{"name":"Needs automation","description":"Issues that needs automated tests","color":""},"Prepared statements":{"name":"Prepared statements","description":"Issues related to prepared statement flow","color":""},"Switch Group Widget":{"name":"Switch Group Widget","description":"Issues related to Switch group Widget","color":""},"Supervisor":{"name":"Supervisor","description":"Issues related to supervisor","color":"2c5813"},"Deployment Certificates":{"name":"Deployment Certificates","description":"Issues related to lets encrypt","color":"e148aa"},"Mock Data":{"name":"Mock Data","description":"Issues related to mock databases","color":"ebf251"},"AWS ECS":{"name":"AWS ECS","description":"Issues related to ECS Fargate","color":"e506ff"},"Publish App":{"name":"Publish App","description":"Issues related to app deployment","color":""},"IDE Infra":{"name":"IDE Infra","description":"Issues related to the IDE infrastructure like saving changes","color":"4c1858"},"User Profile":{"name":"User Profile","description":"Issues related to a user profile","color":"a60d34"},"Admin Settings":{"color":"32a316","name":"Admin Settings","description":"Issues related to admin settings"},"Workspace settings":{"name":"Workspace settings","description":"Issues related to workspace settings","color":"47d1ad"},"Page Management":{"color":"e17a68","name":"Page Management","description":"Issues related to configuring pages"},"Test":{"name":"Test","description":"","color":"33515b"},"Ingress":{"name":"Ingress","description":"Ingress Controller","color":"a86802"},"Nginx":{"name":"Nginx","description":"Issues related to Nginx","color":"e54195"},"Workflows":{"name":"Workflows","description":"","color":"1b89db"},"Building blocks":{"name":"Building blocks","description":"Building blocks on cavas, on templates listing or drag and drop of building blocks.","color":"8e3c7a"},"Widget design system POD":{"name":"Widget design system POD","description":"","color":"bbeecd"},"Table Inline Edit":{"name":"Table Inline Edit","description":"Issues related to inline editing","color":"60895a"}},"success":true} \ No newline at end of file +{"runners":[{"versioning":{"source":"milestones","type":"SemVer"},"prereleaseName":"alpha","issue":{"labels":{"Error Handling":{"conditions":[],"requires":1},"Team Managers Pod":{"conditions":[{"label":"SSO","type":"hasLabel","value":true},{"label":"RBAC","type":"hasLabel","value":true},{"label":"Audit Logs","type":"hasLabel","value":true},{"label":"Airgap","type":"hasLabel","value":true},{"label":"Enterprise Edition","type":"hasLabel","value":true},{"label":"SCIM","type":"hasLabel","value":true},{"label":"Invite flow","type":"hasLabel","value":true},{"label":"User Profile","type":"hasLabel","value":true},{"label":"Admin Settings","type":"hasLabel","value":true},{"label":"Workspace settings","type":"hasLabel","value":true}],"requires":1},"New Developers Pod":{"conditions":[{"label":"Omnibar","type":"hasLabel","value":true},{"label":"Telemetry","type":"hasLabel","value":true},{"label":"Entity Explorer","type":"hasLabel","value":true},{"label":"IDE","type":"hasLabel","value":true},{"label":"i18n","type":"hasLabel","value":true},{"label":"IDE Navigation","type":"hasLabel","value":true},{"label":"In App Comms","type":"hasLabel","value":true},{"label":"App setting","type":"hasLabel","value":true}],"requires":1},"BE Coders Pod":{"conditions":[{"label":"SAAS Plugins","type":"hasLabel","value":true},{"label":"Data Platform Pod","type":"hasLabel","value":true},{"label":"Integrations Pod","type":"hasLabel","value":true}],"requires":1},"FE Coders Pod":{"conditions":[{"label":"JS Linting & Errors","type":"hasLabel","value":true},{"label":"Debugger","type":"hasLabel","value":true},{"label":"Autocomplete","type":"hasLabel","value":true},{"label":"Evaluated Value","type":"hasLabel","value":true},{"label":"Slash Command","type":"hasLabel","value":true},{"label":"New JS Function","type":"hasLabel","value":true},{"label":"JS Usability","type":"hasLabel","value":true},{"label":"OnPageLoad","type":"hasLabel","value":true},{"label":"Framework Functions","type":"hasLabel","value":true},{"label":"JS Objects","type":"hasLabel","value":true},{"label":"JS Evaluation","type":"hasLabel","value":true},{"label":"AST-frontend","type":"hasLabel","value":true},{"label":"Custom JS Libraries","type":"hasLabel","value":true},{"label":"Action Selector","type":"hasLabel","value":true},{"label":"Widget setter method","type":"hasLabel","value":true},{"label":"Error Handling","type":"hasLabel","value":true}],"requires":1},"App Viewers Pod":{"conditions":[{"label":"Button Widget","type":"hasLabel","value":true},{"label":"Chart Widget","type":"hasLabel","value":true},{"label":"Container Widget","type":"hasLabel","value":true},{"label":"Date Picker Widget","type":"hasLabel","value":true},{"label":"Select Widget","type":"hasLabel","value":true},{"label":"File Picker Widget","type":"hasLabel","value":true},{"label":"Form Widget","type":"hasLabel","value":true},{"label":"Image Widget","type":"hasLabel","value":true},{"label":"Input Widget","type":"hasLabel","value":true},{"label":"List Widget","type":"hasLabel","value":true},{"label":"MultiSelect Widget","type":"hasLabel","value":true},{"label":"Map Widget","type":"hasLabel","value":true},{"label":"Modal Widget","type":"hasLabel","value":true},{"label":"Radio Widget","type":"hasLabel","value":true},{"label":"Rich Text Editor Widget","type":"hasLabel","value":true},{"label":"Tab Widget","type":"hasLabel","value":true},{"label":"Table Widget","type":"hasLabel","value":true},{"label":"Text Widget","type":"hasLabel","value":true},{"label":"Video Widget","type":"hasLabel","value":true},{"label":"iFrame","type":"hasLabel","value":true},{"label":"Menu Button","type":"hasLabel","value":true},{"label":"Rating","type":"hasLabel","value":true},{"label":"Widget Validation","type":"hasLabel","value":true},{"label":"reallabel","type":"hasLabel","value":true},{"label":"New Widget","type":"hasLabel","value":true},{"label":"Switch widget","type":"hasLabel","value":true},{"label":"Audio Widget","type":"hasLabel","value":true},{"label":"Icon Button Widget","type":"hasLabel","value":true},{"label":"Stat Box Widget","type":"hasLabel","value":true},{"label":"Voice Recorder Widget","type":"hasLabel","value":true},{"label":"Calendar Widget","type":"hasLabel","value":true},{"label":"Menu Button Widget","type":"hasLabel","value":true},{"label":"Divider Widget","type":"hasLabel","value":true},{"label":"Rating Widget","type":"hasLabel","value":true},{"label":"View Mode","type":"hasLabel","value":true},{"label":"Widget Property","type":"hasLabel","value":true},{"label":"Document Viewer Widget","type":"hasLabel","value":true},{"label":"Radio Group Widget","type":"hasLabel","value":true},{"label":"Currency Input Widget","type":"hasLabel","value":true},{"label":"TreeSelect","type":"hasLabel","value":true},{"label":"MultiTree Select Widget","type":"hasLabel","value":true},{"label":"Phone Input Widget","type":"hasLabel","value":true},{"label":"JSON Form","type":"hasLabel","value":true},{"label":"All Widgets","type":"hasLabel","value":true},{"label":"Button Group widget","type":"hasLabel","value":true},{"label":"Progress bar widget","type":"hasLabel","value":true},{"label":"Audio Recorder Widget","type":"hasLabel","value":true},{"label":"Camera Widget","type":"hasLabel","value":true},{"label":"Table Widget V2","type":"hasLabel","value":true},{"label":"Branding","type":"hasLabel","value":true},{"label":"Map Chart Widget","type":"hasLabel","value":true},{"label":"Code Scanner Widget","type":"hasLabel","value":true},{"label":"Widget keyboard accessibility","type":"hasLabel","value":true},{"label":"List Widget V2","type":"hasLabel","value":true},{"label":"Slider Widget","type":"hasLabel","value":true},{"label":"One-click Binding","type":"hasLabel","value":true},{"label":"Old widget version","type":"hasLabel","value":true},{"label":"Widget Discoverability","type":"hasLabel","value":true},{"label":"Custom widgets","type":"hasLabel","value":true},{"label":"Switch Group Widget","type":"hasLabel","value":true},{"label":"Checkbox Group widget","type":"hasLabel","value":true},{"label":"Checkbox Widget","type":"hasLabel","value":true},{"label":"Table Inline Edit","type":"hasLabel","value":true}],"requires":1},"UI Builders Pod":{"conditions":[{"label":"Property Pane","type":"hasLabel","value":true},{"label":"Copy Paste","type":"hasLabel","value":true},{"label":"Drag & Drop","type":"hasLabel","value":true},{"label":"Undo/Redo","type":"hasLabel","value":true},{"label":"Widgets Pane","type":"hasLabel","value":true},{"label":"UI Performance","type":"hasLabel","value":true},{"label":"Widget Grouping","type":"hasLabel","value":true},{"label":"Reflow & Resize","type":"hasLabel","value":true},{"label":"Canvas / Grid","type":"hasLabel","value":true},{"label":"Auto Height","type":"hasLabel","value":true},{"label":"Responsive Canvas","type":"hasLabel","value":true},{"label":"Responsive Widget","type":"hasLabel","value":true},{"label":"Responsive Viewport","type":"hasLabel","value":true},{"label":"Spacing","type":"hasLabel","value":true},{"label":"Browser specific","type":"hasLabel","value":true},{"label":"Auto Layout","type":"hasLabel","value":true},{"label":"Fixed layout","type":"hasLabel","value":true},{"label":"Anvil layout","type":"hasLabel","value":true},{"label":"App Navigation","type":"hasLabel","value":true}],"requires":1},"User Education Pod":{"conditions":[{"label":"Documentation","type":"hasLabel","value":true}],"requires":1},"DevOps Pod":{"conditions":[{"label":"Docker","type":"hasLabel","value":true},{"label":"Super Admin","type":"hasLabel","value":true},{"label":"Deployment","type":"hasLabel","value":true},{"label":"K8s","type":"hasLabel","value":true},{"label":"Email Config","type":"hasLabel","value":true},{"label":"Backup & Restore","type":"hasLabel","value":true},{"label":"AWS AMI","type":"hasLabel","value":true},{"label":"Observability","type":"hasLabel","value":true},{"label":"Heroku","type":"hasLabel","value":true},{"label":"New Deployment Mode","type":"hasLabel","value":true},{"label":"Supervisor","type":"hasLabel","value":true},{"label":"Deployment Certificates","type":"hasLabel","value":true},{"label":"Mock Data","type":"hasLabel","value":true},{"label":"AWS ECS","type":"hasLabel","value":true},{"label":"Ingress","type":"hasLabel","value":true},{"label":"Nginx","type":"hasLabel","value":true}],"requires":1},"Design System Pod":{"conditions":[{"label":"Design System Pod","type":"hasLabel","value":true},{"label":"ADS Component Issue","type":"hasLabel","value":true},{"label":"Keyboard accessibility ","type":"hasLabel","value":true},{"label":"Toggle button","type":"hasLabel","value":true},{"label":"ADS Category Token","type":"hasLabel","value":true},{"label":"ADS Component Documentation","type":"hasLabel","value":true},{"label":"ADS Migration","type":"hasLabel","value":true},{"label":"ADS Deduplication ","type":"hasLabel","value":true},{"label":"ADS Revamp","type":"hasLabel","value":true},{"label":"ADS Deduplication","type":"hasLabel","value":true},{"label":"ADS Unit Test","type":"hasLabel","value":true},{"label":"ADS Components","type":"hasLabel","value":true},{"label":"ADS Grayscale","type":"hasLabel","value":true},{"label":"Design System","type":"hasLabel","value":true},{"label":"ADS Typography","type":"hasLabel","value":true},{"label":"ADS Visual Styles","type":"hasLabel","value":true},{"label":"ADS Component Design","type":"hasLabel","value":true},{"label":"Modal Component","type":"hasLabel","value":true}],"requires":1},"Data Platform Pod":{"conditions":[{"label":"Datasource Environments","type":"hasLabel","value":true},{"label":"Datatype issue","type":"hasLabel","value":true},{"label":"Entity Refactor","type":"hasLabel","value":true},{"label":"Core Query Execution","type":"hasLabel","value":true},{"label":"Query Management","type":"hasLabel","value":true},{"label":"Query Settings","type":"hasLabel","value":true},{"label":"SmartSubstitution","type":"hasLabel","value":true},{"label":"Query Generation","type":"hasLabel","value":true},{"label":"Query performance","type":"hasLabel","value":true},{"label":"Suggested Widgets","type":"hasLabel","value":true},{"label":"Page load executions","type":"hasLabel","value":true},{"label":"DSL Update","type":"hasLabel","value":true},{"label":"AST-backend","type":"hasLabel","value":true},{"label":"File upload issues","type":"hasLabel","value":true},{"label":"DocumentDB","type":"hasLabel","value":true},{"label":"Multiple Environments","type":"hasLabel","value":true},{"label":"Platformization","type":"hasLabel","value":true},{"label":"Custom environments","type":"hasLabel","value":true},{"label":"Schema","type":"hasLabel","value":true},{"label":"Secret Management","type":"hasLabel","value":true},{"label":"Publish App","type":"hasLabel","value":true}],"requires":1},"Integrations Pod":{"conditions":[{"label":"New Datasource","type":"hasLabel","value":true},{"label":"Firestore","type":"hasLabel","value":true},{"label":"Google Sheets","type":"hasLabel","value":true},{"label":"Mongo","type":"hasLabel","value":true},{"label":"Redshift","type":"hasLabel","value":true},{"label":"snowflake","type":"hasLabel","value":true},{"label":"S3","type":"hasLabel","value":true},{"label":"Redis","type":"hasLabel","value":true},{"label":"Postgres","type":"hasLabel","value":true},{"label":"GraphQL Plugin","type":"hasLabel","value":true},{"label":"ArangoDB","type":"hasLabel","value":true},{"label":"MsSQL","type":"hasLabel","value":true},{"label":"Elastic Search","type":"hasLabel","value":true},{"label":"OAuth","type":"hasLabel","value":true},{"label":"Airtable","type":"hasLabel","value":true},{"label":"CURL","type":"hasLabel","value":true},{"label":"DynamoDB","type":"hasLabel","value":true},{"label":"Zendesk","type":"hasLabel","value":true},{"label":"Hubspot","type":"hasLabel","value":true},{"label":"Query Forms","type":"hasLabel","value":true},{"label":"Twilio","type":"hasLabel","value":true},{"label":"MySQL","type":"hasLabel","value":true},{"label":"Connection pool","type":"hasLabel","value":true},{"label":"MariaDB","type":"hasLabel","value":true},{"label":"Integrations Pod General","type":"hasLabel","value":true},{"label":"SMTP plugin","type":"hasLabel","value":true},{"label":"Oracle SQL DB","type":"hasLabel","value":true},{"label":"Query filter","type":"hasLabel","value":true},{"label":"Activation - datasources","type":"hasLabel","value":true},{"label":"Onboarding","type":"hasLabel","value":true},{"label":"Generate Page","type":"hasLabel","value":true},{"label":"Sniping Mode","type":"hasLabel","value":true},{"label":"Welcome Screen","type":"hasLabel","value":true},{"label":"Login / Signup","type":"hasLabel","value":true},{"label":"REST API","type":"hasLabel","value":true},{"label":"REST API","type":"hasLabel","value":true},{"label":"Activation - learnability","type":"hasLabel","value":true},{"label":"Datasources","type":"hasLabel","value":true},{"label":"REST API plugin","type":"hasLabel","value":true},{"label":"Prepared statements","type":"hasLabel","value":true}],"requires":1},"Git Pod":{"conditions":[{"label":"Git Version Control","type":"hasLabel","value":true},{"label":"Import-Export-App","type":"hasLabel","value":true},{"label":"Fork App","type":"hasLabel","value":true},{"label":"Git Auto-commit","type":"hasLabel","value":true}],"requires":1},"Mobile Pod":{"conditions":[],"requires":1},"Billing & Usage Pod":{"conditions":[{"label":"CE Instance","type":"hasLabel","value":true},{"label":"Customer Portal","type":"hasLabel","value":true},{"label":"Cloud Services","type":"hasLabel","value":true},{"label":"Billing Integrations","type":"hasLabel","value":true},{"label":"Billing","type":"hasLabel","value":true},{"label":"Self Serve","type":"hasLabel","value":true},{"label":"Enterprise Billing","type":"hasLabel","value":true},{"label":"In-app ramps","type":"hasLabel","value":true},{"label":"Analytics Improvements","type":"hasLabel","value":true},{"label":"Self Serve 1.0","type":"hasLabel","value":true},{"label":"License","type":"hasLabel","value":true},{"label":"Appsmith Business Cloud","type":"hasLabel","value":true},{"label":"BE instance","type":"hasLabel","value":true},{"label":"Embedding Apps","type":"hasLabel","value":true},{"label":"TM_BU","type":"hasLabel","value":true},{"label":"Feature Flagging","type":"hasLabel","value":true},{"label":"Invite flow","type":"hasLabel","value":true},{"label":"Invite users","type":"hasLabel","value":true},{"label":"Home Page","type":"hasLabel","value":true},{"label":"1-click upgrade","type":"hasLabel","value":true}],"requires":1},"Performance Pod":{"conditions":[{"label":"Performance","type":"hasLabel","value":true},{"label":"Performance infra","type":"hasLabel","value":true}],"requires":1},"IDE Pod":{"conditions":[{"label":"Preview mode","type":"hasLabel","value":true},{"label":"IDE Infra","type":"hasLabel","value":true},{"label":"Page Management","type":"hasLabel","value":true}],"requires":1},"Appsmith Labs":{"conditions":[{"label":"AI","type":"hasLabel","value":true},{"label":"Knowledge Retrieval","type":"hasLabel","value":true}],"requires":1},"Workflows Pod":{"conditions":[{"label":"Workflows","type":"hasLabel","value":true}],"requires":1},"Modules pod":{"conditions":[{"label":"Module creator","type":"hasLabel","value":true},{"label":"Module consumer","type":"hasLabel","value":true},{"label":"Package","type":"hasLabel","value":true},{"label":"Package versioning","type":"hasLabel","value":true},{"label":"Convert to module","type":"hasLabel","value":true},{"label":"Query module","type":"hasLabel","value":true},{"label":"JS module","type":"hasLabel","value":true},{"label":"UI module","type":"hasLabel","value":true}],"requires":1},"Templates Pod":{"conditions":[{"label":"Templates","type":"hasLabel","value":true},{"label":"Partial-import-export","type":"hasLabel","value":true},{"label":"Building blocks","type":"hasLabel","value":true}],"requires":1},"QA Pod":{"conditions":[{"label":"QA","type":"hasLabel","value":true},{"label":"Automation Test","type":"hasLabel","value":true},{"label":"TestGap","type":"hasLabel","value":true},{"label":"Automation failures","type":"hasLabel","value":true},{"label":"Needs automation","type":"hasLabel","value":true}],"requires":1},"Widget design system POD":{"conditions":[{"label":"App Theming","type":"hasLabel","value":true},{"label":"Widget Styling","type":"hasLabel","value":true},{"label":"Checkbox Component","type":"hasLabel","value":true},{"label":"WDS team","type":"hasLabel","value":true},{"label":"Widget design system POD","type":"hasLabel","value":true}],"requires":1}}},"root":"."}],"labels":{"Tab Widget":{"color":"e2c76c","name":"Tab Widget","description":""},"Dont merge":{"color":"ADB39C","name":"Dont merge","description":""},"Epic":{"color":"3E4B9E","name":"Epic","description":"A zenhub epic that describes a project"},"Menu Button Widget":{"color":"235708","name":"Menu Button Widget","description":"Issues related to Menu Button widget"},"Checkbox Group widget":{"color":"bbeecd","name":"Checkbox Group widget","description":"Issues related to Checkbox Group Widget"},"Input Widget":{"color":"ae65d8","name":"Input Widget","description":""},"Security":{"color":"99139C","name":"Security","description":""},"QA":{"color":"","name":"QA","description":"Needs QA attention"},"Verified":{"color":"9bf416","name":"Verified","description":""},"Wont Fix":{"color":"ffffff","name":"Wont Fix","description":"This will not be worked on"},"MySQL":{"color":"c9ddc6","name":"MySQL","description":"Issues related to MySQL plugin"},"Development":{"color":"9F8A02","name":"Development","description":""},"Help Wanted":{"color":"008672","name":"Help Wanted","description":"Extra attention is needed"},"Home Page":{"color":"9c0c8e","name":"Home Page","description":"Issues related to the application home page"},"Rating Widget":{"color":"235708","name":"Rating Widget","description":"Issues related to the rating widget"},"Stat Box Widget":{"color":"f1c9ce","name":"Stat Box Widget","description":"Issues related to stat box"},"Enhancement":{"color":"a2eeef","name":"Enhancement","description":"New feature or request"},"Fork App":{"color":"30c76d","name":"Fork App","description":"Issues related to forking apps"},"Container Widget":{"color":"19AD0D","name":"Container Widget","description":"Container widget"},"Papercut":{"color":"B562F6","name":"Papercut","description":""},"Needs Design":{"color":"bfd4f2","name":"Needs Design","description":"needs design or changes to design"},"i18n":{"color":"1799b0","name":"i18n","description":"Represents issues that need to be tackled to handle internationalization"},"Rich Text Editor Widget":{"color":"f72cac","name":"Rich Text Editor Widget","description":""},"Onboarding":{"color":"30c76d","name":"Onboarding","description":"Issues related to onboarding new developers"},"skip-changelog":{"color":"06086F","name":"skip-changelog","description":"Adding this label to a PR prevents it from being listed in the changelog"},"Low":{"color":"79e53b","name":"Low","description":"An issue that is neither critical nor breaks a user flow"},"potential-duplicate":{"color":"d3cb2e","name":"potential-duplicate","description":"This label marks issues that are potential duplicates of already open issues"},"Audio Widget":{"color":"447B9A","name":"Audio Widget","description":"Issues related to Audio Widget"},"Firestore":{"color":"8078b0","name":"Firestore","description":"Issues related to the firestore Integration"},"New Widget":{"color":"be4cf2","name":"New Widget","description":"A request for a new widget"},"Modal Widget":{"color":"03846f","name":"Modal Widget","description":""},"UX Improvement":{"color":"f4a089","name":"UX Improvement","description":""},"S3":{"color":"8078b0","name":"S3","description":"Issues related to the S3 plugin"},"Release Blocker":{"color":"5756bf","name":"Release Blocker","description":"This issue must be resolved before the release"},"safari":{"color":"51C6AA","name":"safari","description":"Bugs seen on safari browser"},"Example Apps":{"color":"1799b0","name":"Example Apps","description":"Example apps created for new signups"},"MultiSelect Widget":{"color":"AB62D4","name":"MultiSelect Widget","description":"Issues related to MultiSelect Widget"},"Widget Styling":{"color":"905420","name":"Widget Styling","description":"all about widget styling"},"Calendar Widget":{"color":"8c6644","name":"Calendar Widget","description":""},"Website":{"color":"151720","name":"Website","description":"Related to www.appsmith.com website"},"Low effort":{"color":"8B59F0","name":"Low effort","description":"Something that'll take a few days to build"},"App Viewers Pod":{"color":"cd8ef9","name":"App Viewers Pod","description":"This label assigns issues to the app viewers pod"},"Checkbox Widget":{"color":"bbeecd","name":"Checkbox Widget","description":""},"Spam":{"color":"620faf","name":"Spam","description":""},"Voice Recorder Widget":{"color":"85bc87","name":"Voice Recorder Widget","description":""},"Select Widget":{"color":"0c669e","name":"Select Widget","description":"Select or dropdown widget"},"Bug":{"color":"8ba6fd","name":"Bug","description":"Something isn't right"},"Widget Validation":{"color":"6990BC","name":"Widget Validation","description":"Issues related to widget property validation"},"Generate Page":{"color":"30c76d","name":"Generate Page","description":"Issures related to page generation"},"File Picker Widget":{"color":"6ae4f2","name":"File Picker Widget","description":""},"snowflake":{"color":"8078b0","name":"snowflake","description":"Issues related to the snowflake Integration"},"Automation":{"color":"CCAF60","name":"Automation","description":""},"hotfix":{"color":"BA3F1D","name":"hotfix","description":""},"Team Managers Pod":{"color":"bddb81","name":"Team Managers Pod","description":"Issues that team managers care about for the security and efficiency of their teams"},"Import-Export-App":{"color":"15076d","name":"Import-Export-App","description":"Issues related to importing and exporting apps"},"High effort":{"color":"A7E87B","name":"High effort","description":"Something that'll take more than a month to build"},"Telemetry":{"color":"bc70f9","name":"Telemetry","description":"Issues related to instrumenting appsmith"},"Radio Widget":{"color":"91ef15","name":"Radio Widget","description":""},"Omnibar":{"color":"10b5ce","name":"Omnibar","description":"Issues related to the omnibar for navigation"},"Button Widget":{"color":"34efae","name":"Button Widget","description":""},"Switch widget":{"color":"33A8CE","name":"Switch widget","description":"The switch widget"},"Map Widget":{"color":"7eef7a","name":"Map Widget","description":""},"Task":{"color":"085630","name":"Task","description":"A simple Todo"},"Design System":{"color":"2958a4","name":"Design System","description":"Design system"},"opera":{"color":"C63F5B","name":"opera","description":"Any issues identified on the opera browser"},"Login / Signup":{"color":"30c76d","name":"Login / Signup","description":"Authentication flows"},"Image Widget":{"color":"8de8ad","name":"Image Widget","description":""},"firefox":{"color":"6d56e2","name":"firefox","description":""},"Property Pane":{"color":"b356ff","name":"Property Pane","description":"Issues related to the behaviour of the property pane"},"Deployment":{"color":"93491f","name":"Deployment","description":"Installation process of appsmith"},"IDE":{"color":"61b2ee","name":"IDE","description":"Issues related to the IDE"},"Production":{"color":"b60205","name":"Production","description":""},"Dependencies":{"color":"0366d6","name":"Dependencies","description":"Pull requests that update a dependency file"},"Google Sheets":{"color":"8078b0","name":"Google Sheets","description":"Issues related to Google Sheets"},"Icon Button Widget":{"color":"D319CE","name":"Icon Button Widget","description":"Issues related to the icon button widget"},"Mongo":{"color":"8078b0","name":"Mongo","description":"Issues related to Mongo DB plugin"},"Documentation":{"color":"a8dff7","name":"Documentation","description":"Improvements or additions to documentation"},"TestGap":{"color":"","name":"TestGap","description":"Issues identified for test plan improvement"},"keyboard shortcut":{"color":"0688B6","name":"keyboard shortcut","description":""},"Git Version Control":{"color":"858172","name":"Git Version Control","description":"Issues related to version control"},"Reopen":{"color":"897548","name":"Reopen","description":""},"Redshift":{"color":"8078b0","name":"Redshift","description":"Issues related to the redshift integration"},"Date Picker Widget":{"color":"ef1ce1","name":"Date Picker Widget","description":""},"Entity Explorer":{"color":"a2e2f9","name":"Entity Explorer","description":"Issues related to navigation using the entity explorer"},"JS Linting & Errors":{"color":"E56AA5","name":"JS Linting & Errors","description":"Issues related to JS Linting and errors"},"iFrame":{"color":"3CD1DB","name":"iFrame","description":"Issues related to iFrame"},"Stale":{"color":"ededed","name":"Stale","description":null},"Debugger":{"color":"e79062","name":"Debugger","description":"Issues related to the debugger"},"Text Widget":{"color":"d130d1","name":"Text Widget","description":""},"Video Widget":{"color":"23dd4b","name":"Video Widget","description":""},"Datasources":{"color":"3d590f","name":"Datasources","description":"Issues related to configuring datasource on appsmith"},"error":{"color":"B66773","name":"error","description":"All issues connected to error messages"},"Form Widget":{"color":"09ed77","name":"Form Widget","description":""},"Needs Triaging":{"color":"e8b851","name":"Needs Triaging","description":"Needs attention from maintainers to triage"},"Autocomplete":{"color":"235708","name":"Autocomplete","description":"Issues related to the autocomplete"},"hacktoberfest":{"color":"0052cc","name":"hacktoberfest","description":"All issues that can be solved by the community during Hacktoberfest"},"Medium effort":{"color":"D31156","name":"Medium effort","description":"Something that'll take more than a week but less than a month to build"},"Release":{"color":"57e5e0","name":"Release","description":""},"High":{"color":"c94d14","name":"High","description":"This issue blocks a user from building or impacts a lot of users"},"UI Performance":{"color":"1799b0","name":"UI Performance","description":"Issues related to UI performance"},"UI Builders Pod":{"color":"517fba","name":"UI Builders Pod","description":"Issues that UI Builders face using appsmith"},"Deploy Preview":{"color":"bfdadc","name":"Deploy Preview","description":"Issues found in Deploy Preview"},"Needs Tests":{"color":"8ee263","name":"Needs Tests","description":"Needs automated tests to assert a feature/bug fix"},"Refactor":{"color":"B96662","name":"Refactor","description":"needs refactoring of code"},"Divider Widget":{"color":"235708","name":"Divider Widget","description":"Issues related to the divider widget"},"Table Widget":{"color":"2eead1","name":"Table Widget","description":""},"Needs More Info":{"color":"e54c10","name":"Needs More Info","description":"Needs additional information"},"Good First Issue":{"color":"7057ff","name":"Good First Issue","description":"Good for newcomers"},"UI Improvement":{"color":"9aeef4","name":"UI Improvement","description":""},"Backend":{"color":"d4c5f9","name":"Backend","description":"This marks the issue or pull request to reference server code"},"Frontend":{"color":"87c7f2","name":"Frontend","description":"This label marks the issue or pull request to reference client code"},"In App Comms":{"name":"In App Comms","description":"Issues around communication with appsmith instances","color":"463cca"},"Chart Widget":{"color":"616ecc","name":"Chart Widget","description":""},"List Widget":{"color":"8508A0","name":"List Widget","description":"Issues related to the list widget"},"Duplicate":{"color":"cfd3d7","name":"Duplicate","description":"This issue or pull request already exists"},"JS Snippets":{"color":"8d62d2","name":"JS Snippets","description":"issues related to JS Snippets"},"Copy Paste":{"name":"Copy Paste","description":"Issues related to copy paste","color":"b4f0a9"},"Drag & Drop":{"name":"Drag & Drop","description":"Issues related to the drag & drop experience","color":"92115a"},"BE Coders Pod":{"color":"5d9848","name":"BE Coders Pod","description":"Issues related to users writing code to fetch and update data"},"FE Coders Pod":{"color":"a7effc","name":"FE Coders Pod","description":"Issues related to users writing javascript in appsmith"},"New Developers Pod":{"color":"6310da","name":"New Developers Pod","description":"Issues that new developers face while exploring the IDE"},"Sniping Mode":{"name":"Sniping Mode","description":"Issues related to sniping mode","color":"30c76d"},"Redis":{"name":"Redis","description":"Issues related to Redis","color":"8078b0"},"New Datasource":{"color":"60b14c","name":"New Datasource","description":"Requests for new datasources"},"Evaluated Value":{"name":"Evaluated Value","description":"Issues related to evaluated values","color":"39f6e7"},"Undo/Redo":{"name":"Undo/Redo","description":"Issues related to undo/redo","color":"f25880"},"App Navigation":{"name":"App Navigation","description":"Issues related to the topbar navigation and configuring it","color":"4773ab"},"Responsive Viewport":{"color":"d12d2e","name":"Responsive Viewport","description":"Issues seen on different viewports like mobile"},"Widgets Pane":{"name":"Widgets Pane","description":"Issues related to the discovery and organisation of widgets","color":"ad5d78"},"View Mode":{"color":"1799b0","name":"View Mode","description":"Issues related to the view mode"},"User Education Pod":{"name":"User Education Pod","description":"Issues related to user education","color":"1799b0"},"Content":{"name":"Content","description":"For content related topics i.e blogs, templates, videos","color":"a8dff7"},"Embedding Apps":{"name":"Embedding Apps","description":"Issues related to embedding","color":"30c76d"},"Slash Command":{"name":"Slash Command","description":"Issues related to the slash command","color":"a0608e"},"Widget Property":{"name":"Widget Property","description":"Issues related to adding / modifying widget properties across widgets","color":"5e92cb"},"Windows":{"name":"Windows","description":"Issues related exclusively to Windows systems","color":"b4cb8a"},"Old App Issues":{"name":"Old App Issues","description":"Issues related to apps old apps a few weeks old and app issues in stale browser session","color":"87ab18"},"Document Viewer Widget":{"name":"Document Viewer Widget","description":"Issues related to Document Viewer Widget","color":"899d4b"},"Radio Group Widget":{"name":"Radio Group Widget","description":"Issues related to radio group widget","color":"b68495"},"Super Admin":{"name":"Super Admin","description":"Issues related to the super admin page","color":"aa95cf"},"Postgres":{"name":"Postgres","description":"Postgres related issues","color":"8078b0"},"New JS Function":{"name":"New JS Function","description":"Issues related to adding a JS Function","color":"8e8aa4"},"Cannot Reproduce Issue":{"color":"93c9cc","name":"Cannot Reproduce Issue","description":"Issues that cannot be reproduced"},"Widget Grouping":{"name":"Widget Grouping","description":"Issues related to Widget Grouping","color":"a49951"},"K8s":{"name":"K8s","description":"Kubernetes related issues","color":"5f318a"},"Docker":{"name":"Docker","description":"Issues related to docker","color":"89b808"},"Camera Widget":{"name":"Camera Widget","description":"Issues and enhancements related to camera widget","color":"e6038e"},"SAAS Plugins":{"name":"SAAS Plugins","description":"Issues related to SAAS Plugins","color":"ef9c9d"},"JS Promises":{"name":"JS Promises","description":"Issues related to promises","color":"d7771f"},"OnPageLoad":{"name":"OnPageLoad","description":"OnPageLoad issues on functions and queries","color":"50559d"},"JS Usability":{"name":"JS Usability","description":"usability issues with JS editor and JS elsewhere","color":"a302b0"},"Currency Input Widget":{"name":"Currency Input Widget","description":"Issues related to currency input widget","color":"b2164f"},"TreeSelect":{"name":"TreeSelect","description":"Issues related to TreeSelect Widget","color":"a1633e"},"MultiTree Select Widget":{"name":"MultiTree Select Widget","description":"Issues related to MultiTree Select Widget","color":"a1633e"},"Welcome Screen":{"name":"Welcome Screen","description":"Issues related to the welcome screen","color":"30c76d"},"Realtime Commenting":{"color":"a70b86","name":"Realtime Commenting","description":"In-app communication between teams"},"Phone Input Widget":{"name":"Phone Input Widget","description":"Issues related to the Phone Input widget","color":"a70b86"},"JSON Form":{"name":"JSON Form","description":"Issue / features related to the JSON form wiget","color":"46b209"},"All Widgets":{"name":"All Widgets","description":"Issues related to all widgets","color":"972b36"},"V1":{"name":"V1","description":"V1","color":"67ab2e"},"Reflow & Resize":{"name":"Reflow & Resize","description":"All issues related to reflow and resize experience","color":"748a13"},"App Theming":{"name":"App Theming","description":"Items that are related to the App level theming controls epic","color":"905420"},"SSO":{"name":"SSO","description":"Issues, requests and enhancements around Single sign-on.","color":"bf019b"},"Multi User Realtime":{"name":"Multi User Realtime","description":"Issues related to multiple users using or editing an application","color":"e7b6ce"},"Templates":{"name":"Templates","description":"Issues related to templates","color":"b893f6"},"Ready for design":{"name":"Ready for design","description":"this issue is ready for design: it contains clear problem statements and other required information","color":"ebf442"},"Support":{"name":"Support","description":"Issues created by the A-force team to address user queries","color":"1740f3"},"Button Group widget":{"name":"Button Group widget","description":"Issue and enhancements related to the button group widget","color":"f17025"},"GraphQL Plugin":{"name":"GraphQL Plugin","description":"Issues related to GraphQL plugin","color":"8078b0"},"DevOps Pod":{"name":"DevOps Pod","description":"Issues related to devops","color":"d956c7"},"medium":{"name":"medium","description":"Issues that frustrate users due to poor UX","color":"23dfd9"},"ArangoDB":{"name":"ArangoDB","description":"Issues related to arangoDB","color":"8078b0"},"Code Refactoring":{"name":"Code Refactoring","description":"Issues related to code refactoring","color":"76310e"},"Progress bar widget":{"name":"Progress bar widget","description":"To track issues related to progress bar","color":"2d7abf"},"Audio Recorder Widget":{"name":"Audio Recorder Widget","description":"Issues related to Audio Recorder Widget","color":"9accef"},"Airtable":{"name":"Airtable","description":"Issues for Airtable","color":"60885f"},"RBAC":{"name":"RBAC","description":"Issues, requests and enhancements around RBAC.","color":"9211c3"},"Canvas / Grid":{"name":"Canvas / Grid","description":"Issues related to the canvas","color":"16b092"},"Email Config":{"name":"Email Config","description":"Issues related to configuring the email service","color":"2a21d1"},"CURL":{"name":"CURL","description":"Issues related to CURL impor","color":"60885f"},"Canvas Zooms":{"name":"Canvas Zooms","description":"Issues related to zooming the canvas","color":"e6038e"},"business":{"name":"business","description":"Features that will be a part of our business edition","color":"cd59eb"},"Action Pod":{"name":"Action Pod","description":"","color":"ee2e36"},"AutomationGap1":{"color":"a5e07c","name":"AutomationGap1","description":"Issues that needs automated tests"},"A-Force11":{"name":"A-Force11","description":"Issues raised by A-Force team","color":"d667b6"},"Business Edition":{"name":"Business Edition","description":"Features that will be a part of our business edition","color":"89bb6c"},"storeValue":{"name":"storeValue","description":"Issues related to the store value function","color":"5d3e66"},"DynamoDB":{"name":"DynamoDB","description":"Issues that are related to DynamoDB should have this label","color":"60885f"},"Design System Pod":{"name":"Design System Pod","description":"Appsmith design system related issues","color":"706f03"},"ABAC":{"color":"e009a5","name":"ABAC","description":"User permissions and access controls"},"Backup & Restore":{"name":"Backup & Restore","description":"Issues related to backup and restore","color":"86874d"},"Billing":{"name":"Billing","description":"Billing infrastructure and flows for Business Edition and Trial users","color":"d2bc40"},"Datatype issue":{"name":"Datatype issue","description":"Issues that have risen because data types weren't handled","color":"60885f"},"OAuth":{"name":"OAuth","description":"OAuth related bugs or features","color":"60885f"},"Table Widget V2":{"name":"Table Widget V2","description":"Issues related to Table Widget V2","color":"3a7192"},"IDE Navigation":{"name":"IDE Navigation","description":"Issues/feature requests related to IDE navigation, and context switching","color":"bc0cba"},"Query performance":{"name":"Query performance","description":"Issues that have to do with lack in performance of query execution","color":"e4d966"},"SAAS Manager App":{"name":"SAAS Manager App","description":"Issues with the SAAS manager app","color":"d427db"},"Twilio":{"name":"Twilio","description":"Issues related to Twilio integration","color":"23ba8d"},"Hubspot":{"name":"Hubspot","description":"Issues related to Hubspot integration","color":"60885f"},"Zendesk":{"name":"Zendesk","description":"Issues related to Zendesk integration","color":"60885f"},"Entity Refactor":{"name":"Entity Refactor","description":"Issues related to refactor logic","color":"418fa4"},"Branding":{"name":"Branding","description":"All issues under branding and whitelabelling appsmith ecosystem","color":"7aaaf1"},"Map Chart Widget":{"name":"Map Chart Widget","description":"Issues related to Map Chart Widgets","color":"c8397f"},"Product Catchup":{"name":"Product Catchup","description":"Issues created in the product catchup","color":"29cd2c"},"Framework Functions":{"name":"Framework Functions","description":"Issues related to internal functions like showAlert(), navigateTo() etc...","color":"c25a09"},"Frontend Libraries Upgrade":{"name":"Frontend Libraries Upgrade","description":"Issues related to frontend libraries upgrade","color":"ede1fc"},"Audit Logs":{"name":"Audit Logs","description":"Audit trails to ensure data security","color":"f3fd62"},"MsSQL":{"name":"MsSQL","description":"Issues related to MsSQL plugin","color":"8078b0"},"Data Platform Pod":{"name":"Data Platform Pod","description":"Issues related to the underlying data platform","color":"3f8c3a"},"Integrations Pod":{"name":"Integrations Pod","description":"Issues related to a specific integration","color":"5dbbb1"},"Datasource Environments":{"name":"Datasource Environments","description":"Issues related to datasource environments","color":"bb7a14"},"Elastic Search":{"name":"Elastic Search","description":"Issues related to the elastic search datasource","color":"8078b0"},"Core Query Execution":{"color":"418fa4","name":"Core Query Execution","description":"Issues related to the execution of all queries"},"Query Management":{"name":"Query Management","description":"Issues related to the CRUD of actions or queries","color":"6a5b42"},"Query Settings":{"name":"Query Settings","description":"Issues related to the settings of all queries","color":"c7da7a"},"Code Editor":{"name":"Code Editor","description":"Issues related to the code editor","color":"4ca16e"},"Query Forms":{"color":"12b253","name":"Query Forms","description":"Isuses related to the query forms"},"JS Objects":{"color":"22962c","name":"JS Objects","description":"Issues related to JS Objects"},"JS Evaluation":{"color":"22962c","name":"JS Evaluation","description":"Issues related to JS evaluation on the platform"},"SmartSubstitution":{"name":"SmartSubstitution","description":"Issues related to Smart substitution of mustache bindings in queries","color":"e4d966"},"Query Generation":{"name":"Query Generation","description":"Issues related to query generation","color":"e4d966"},"Suggested Widgets":{"name":"Suggested Widgets","description":"Issues related to suggesting widgets based on query response","color":"e4d966"},"Page load executions":{"name":"Page load executions","description":"Issues related to page load execution","color":"5696b2"},"Code Scanner Widget":{"name":"Code Scanner Widget","description":"Issues related to code scanner widget","color":"9bc1a0"},"Clean URLs":{"name":"Clean URLs","description":"Issues related to clean URLs epic","color":"112623"},"Widget keyboard accessibility":{"name":"Widget keyboard accessibility","description":"All issues related to keyboard accessibility in widgets","color":"b626fd"},"Connection pool":{"name":"Connection pool","description":"issues to do with connection pooling of various plugins","color":"94fe36"},"List Widget V2":{"name":"List Widget V2","description":"Issues related to the list widget v2","color":"adaaf7"},"Auto Height":{"name":"Auto Height","description":"Issues related to dynamic height of widgets","color":"5149cf"},"cypress_failed_test":{"name":"cypress_failed_test","description":"Cypress failed tests","color":"4745d5"},"Needs validation":{"name":"Needs validation","description":"Needs problem validation before being picked up","color":"66673d"},"Slider Widget":{"name":"Slider Widget","description":"Issues raised for slider widgets.","color":"2eef5f"},"Multitenancy":{"name":"Multitenancy","description":"Support multitenancy within single appsmith instance","color":"8c49a9"},"Git Pod":{"name":"Git Pod","description":"Anything related to git sync","color":"2e5ba4"},"Mobile Pod":{"name":"Mobile Pod","description":"All issues related to mobile responsiveness","color":"6c97fd"},"Responsive Widget":{"name":"Responsive Widget","description":"All issues related to widget responsiveness","color":"d12d2e"},"Responsive Canvas":{"name":"Responsive Canvas","description":"All issues related to canvas responsiveness","color":"45a0a8"},"Conversion Algorithm":{"name":"Conversion Algorithm","description":"All issue related to converting app from fixed to flex mode & vice versa","color":"d12d2e"},"Spacing":{"name":"Spacing","description":"All issue related to spacing between widgets in auto layout","color":"d12d2e"},"Browser specific":{"name":"Browser specific","description":"All issue related to browser","color":"d12d2e"},"Error Handling":{"name":"Error Handling","description":"Issues related to error handling","color":"4e1872"},"Performance infra":{"name":"Performance infra","description":"all issue related to the performance infra","color":"8a60f6"},"DSL Update":{"name":"DSL Update","description":"Issues related to storing and updating the DSL","color":"e16cf3"},"AST-frontend":{"name":"AST-frontend","description":"Issues related to maintaining AST logic","color":"434a3a"},"AST-backend":{"name":"AST-backend","description":"Backend issues related to AST parsing","color":"c476eb"},"MariaDB":{"name":"MariaDB","description":"MariaDB datasource","color":"8428c3"},"Billing & Usage Pod":{"name":"Billing & Usage Pod","description":"Issues pertaining to licensing, billing, usage across self serve and enterprise customers","color":"256808"},"ADS Component Issue":{"name":"ADS Component Issue","description":"Issues which are caused due to ADS components","color":"d89119"},"Regressed":{"color":"723fd0","name":"Regressed","description":"Scenarios that were working before but have now regressed"},"Needs RCA":{"name":"Needs RCA","description":"a critical or high priority issue that needs an RCA","color":"2cc68f"},"Custom JS Libraries":{"name":"Custom JS Libraries","description":"Issues related to adding custom JS library","color":"bacb6d"},"Integrations Pod General":{"name":"Integrations Pod General","description":"Issues related to the Integrations Pod that don't fit into other tags.","color":"287823"},"Performance Pod":{"name":"Performance Pod","description":"All things related to Appsmith performance","color":"b5a25d"},"Performance":{"name":"Performance","description":"Issues related to performance","color":"9a18d7"},"File upload issues":{"name":"File upload issues","description":"Issues related to uploading any type of files from within Appsmith","color":"8154df"},"Action Selector":{"name":"Action Selector","description":"Issues related to action selector on the property pane","color":"2f9e20"},"Community Reported":{"name":"Community Reported","description":"issues reported by community members","color":"1402e5"},"JS Function execution":{"name":"JS Function execution","description":"JS function execution","color":"7c2de1"},"Self Serve":{"name":"Self Serve","description":"For all issues related to self-serve flow for business edition","color":"4dacfc"},"Self Serve 1.0":{"name":"Self Serve 1.0","description":"For all issues related to v1 of the self serve project","color":"ae839e"},"CE Instance":{"name":"CE Instance","description":"For all issues relating to usage, licensing or billing on the CE instance","color":"d2bc40"},"Customer Portal":{"name":"Customer Portal","description":"For all tasks/issues pertaining to customer.appsmith.com","color":"d2bc40"},"Cloud Services":{"name":"Cloud Services","description":"For all tasks/issues on Appsmith cloud-services relating to licensing, usage and billing","color":"d2bc40"},"Billing Integrations":{"name":"Billing Integrations","description":"For all issues relating to 3P integrations Appsmith is using for billing & usage","color":"d2bc40"},"One-click Binding":{"name":"One-click Binding","description":"Issues related to the One click binding epic","color":"f1661c"},"Airgap":{"name":"Airgap","description":"Tickets related to supporting air-gapped Appsmith instances","color":"1cb294"},"SMTP plugin":{"name":"SMTP plugin","description":"Issues related to SMTP plugin","color":"541457"},"AWS AMI":{"name":"AWS AMI","description":"Issues Related to AWS AMI","color":"b44680"},"Old widget version":{"name":"Old widget version","description":"Use this label to raise issue specific only to an older version of a widget","color":"ff3814"},"Enterprise Billing":{"name":"Enterprise Billing","description":"To track all tasks/issues related to licensing & billing for enterprise customers","color":"14c156"},"Appsmith Business Cloud":{"name":"Appsmith Business Cloud","description":"Issues related to our business cloud offering","color":"89bb6c"},"Oracle SQL DB":{"name":"Oracle SQL DB","description":"Issues related to the Oracle plugin","color":"cbabcb"},"Community Contributor":{"name":"Community Contributor","description":"Meant to track issues that are assigned to external contributors","color":"149ab6"},"widget vertical alignment":{"name":"widget vertical alignment","description":"All issue related widget vertical alignment on the auto layout canvas","color":"d12d2e"},"Observability":{"name":"Observability","description":"Issues related to observability on the Appsmith instance","color":"dff913"},"Checkbox Component":{"name":"Checkbox Component","description":"This labels deals with checkbox component in wds package","color":"75a401"},"In-app ramps":{"name":"In-app ramps","description":"For all tasks/issues relating to adding in-app ramps in the community edition of the product","color":"8abae0"},"Analytics Improvements":{"name":"Analytics Improvements","description":"For all tasks focused on improving our overall analytics and fixing any issues ","color":"29b8ed"},"WDS team":{"name":"WDS team","description":"","color":"8d675a"},"Enterprise Edition":{"name":"Enterprise Edition","description":"Features that will be supported in Enterprise Edition only","color":"984f5e"},"Query filter":{"name":"Query filter","description":"Issues related to query filtering, e.g., WHERE clause","color":"a15134"},"Keyboard accessibility ":{"name":"Keyboard accessibility ","description":"All issue related to ADS component keyboard accessibility","color":"2ba696"},"Toggle button":{"name":"Toggle button","description":"All issue related to ADS toggle button","color":"edc47f"},"Feature Flagging":{"name":"Feature Flagging","description":"Anything related feature flagging","color":"8d8a09"},"SCIM":{"name":"SCIM","description":"Label to collate our SCIM issues","color":"61a852"},"ADS Category Token":{"name":"ADS Category Token","description":"All issues related appsmith design system category tokens","color":"920961"},"ADS Component Documentation":{"name":"ADS Component Documentation","description":"All issues Appsmith design system component documentation","color":"64c46a"},"ADS Migration":{"name":"ADS Migration","description":"All issues related to Appsmith design system migration","color":"b082d6"},"ADS Deduplication ":{"name":"ADS Deduplication ","description":"Replacing component with ADS components","color":"b082d6"},"ADS Revamp":{"name":"ADS Revamp","description":"All issues related to ads revamp. ","color":"b082d6"},"ADS Deduplication":{"name":"ADS Deduplication","description":"Replacing component with ADS components","color":"b082d6"},"ADS Grayscale":{"name":"ADS Grayscale","description":"Support grayscale color changes","color":"b03577"},"ADS Unit Test":{"name":"ADS Unit Test","description":"All issue related ads unit cases ","color":"b082d6"},"ADS Components":{"name":"ADS Components","description":"All issues related ADS components","color":"b082d6"},"Widget Discoverability":{"name":"Widget Discoverability","description":"Issues related to Widget Discoverability","color":"7b55ce"},"Widget setter method":{"name":"Widget setter method","description":"Issues with widget property setters","color":"8dce87"},"License":{"name":"License","description":"For all issues/tasks related to licensing of appsmith-ee edition","color":"90ee98"},"DocumentDB":{"name":"DocumentDB","description":"Issues related to support DocumentDB in Appsmith Data layer","color":"2c8b56"},"Multiple Environments":{"name":"Multiple Environments","description":"Issues or tasks related to multiple environments","color":"4e972b"},"Platformization":{"name":"Platformization","description":"Issues or tasks related to platformization of Appsmith codebase","color":"4e972b"},"Activation - datasources":{"name":"Activation - datasources","description":"issues related to activation projects","color":"7c7ace"},"Partial-import-export":{"name":"Partial-import-export","description":"Label for granular reusability.","color":"717732"},"AI":{"name":"AI","description":"All tasks related to AI","color":"75c4ce"},"Custom environments":{"name":"Custom environments","description":"Issues with creating or working with custom environments","color":"2137d6"},"ADS Typography":{"name":"ADS Typography","description":"All issue related typographical changes","color":"2dbe8d"},"Auto Layout":{"name":"Auto Layout","description":"Issues relates to auto layout","color":"92cf8c"},"Heroku":{"name":"Heroku","description":"Issues related to Heroku","color":"a81b69"},"ADS Visual Styles":{"name":"ADS Visual Styles","description":"All issues related to ADS visual styles","color":"d3da89"},"ADS Component Design":{"name":"ADS Component Design","description":"All issue related to component design","color":"5cc91e"},"Modal Component":{"name":"Modal Component","description":"All issue related to ads modal component","color":"ee63f3"},"App setting":{"name":"App setting","description":"Related to app settings panel within the app","color":"144206"},"BE instance":{"name":"BE instance","description":"For all issues related to license, billing on BE instance","color":"ae8f98"},"Schema":{"name":"Schema","description":"Issues related to database schema","color":"c470c2"},"Fixed layout":{"name":"Fixed layout","description":"issues related to fixed layout","color":"b66681"},"Anvil layout":{"name":"Anvil layout","description":"issues related to the new layout system anvil","color":"722bf0"},"New Deployment Mode":{"name":"New Deployment Mode","description":"Support a new mode of deployment","color":"108033"},"Custom widgets":{"name":"Custom widgets","description":"For all issues related to the custom widget project","color":"c9db9c"},"IDE Pod":{"name":"IDE Pod","description":"https://app.zenhub.com/workspaces/new-developers-pod-60507ad1d4b98d00150a2858/board","color":"d3d248"},"TM_BU":{"name":"TM_BU","description":"The issues on Team Manager which needs to be taken up by Billing & Usage","color":"198cdf"},"Homepage Experience V2":{"name":"Homepage Experience V2","description":"Label for reporting new tasks and bug fixes related to revamped homepage experience","color":"c55d54"},"Appsmith Labs":{"name":"Appsmith Labs","description":"All things related to AI and other new initiatives ","color":"712d51"},"Customer Success":{"name":"Customer Success","description":"Issues that the success team cares about","color":"6ccabd"},"Invite flow":{"name":"Invite flow","description":"Invite users flow and any associated actions","color":"881b35"},"Invite users":{"name":"Invite users","description":"Invite users flow and any associated actions","color":"23e6d6"},"Workflows Pod":{"name":"Workflows Pod","description":"For all issues related to the Workflows feature","color":"a86802"},"DailyPromotionBlocker":{"name":"DailyPromotionBlocker","description":"DailyPromotion Blocker","color":"9b2280"},"JS Binding":{"name":"JS Binding","description":"All issues related to the JS Binding experience","color":"422fed"},"Knowledge Retrieval":{"name":"Knowledge Retrieval","description":"All issues related to knowledge retrieval on Appsmith AI","color":"a36890"},"REST API":{"name":"REST API","description":"REST API plugin related issues","color":"e3ede5"},"1-click upgrade":{"name":"1-click upgrade","description":"For all issues/tasks related to 1-click upgrade & downgrade project","color":"51b5ff"},"Activation - learnability":{"name":"Activation - learnability","description":"Activation - learnability","color":"96fc76"},"Critical":{"color":"a1e3db","name":"Critical","description":"This issue breaks existing apps. Drop everything else to resolve"},"Modules pod":{"name":"Modules pod","description":"issues that belong to the modules pod","color":"4c6329"},"Module creator":{"name":"Module creator","description":"Issues related to the module creator side","color":"bb2c05"},"Module consumer":{"name":"Module consumer","description":"Issues related to the module consumer side","color":"83d3c5"},"Package":{"name":"Package","description":"Issues related to packages","color":"2ad485"},"Package versioning":{"name":"Package versioning","description":"ISsues related to how we manage versions for packages","color":"4c5218"},"Convert to module":{"name":"Convert to module","description":"Issues related to the module creation flow using conversion","color":"4c5218"},"Query module":{"name":"Query module","description":"Issues affecting query modules or its instances","color":"b11a7e"},"JS module":{"name":"JS module","description":"Issues affecting JS modules or its instances","color":"bf76f6"},"Templates Pod":{"name":"Templates Pod","description":"Issues related to Templates","color":"e7b3b9"},"Secret Management":{"name":"Secret Management","description":"Issues related to secret management","color":"cce8e7"},"REST API plugin":{"name":"REST API plugin","description":"REST API plugin related issues","color":"b5948a"},"UI module":{"name":"UI module","description":"Issues affecting UI modules or its instances","color":"d2acee"},"Preview mode":{"name":"Preview mode","description":"Issues related to app previews","color":"3fb8f2"},"Git Auto-commit":{"name":"Git Auto-commit","description":"Issues related to autocommit","color":"717732"},"QA Pod":{"name":"QA Pod","description":"Issues under the QA Pod","color":"717732"},"Automation Test":{"name":"Automation Test","description":"","color":""},"Automation failures":{"name":"Automation failures","description":"","color":""},"Needs automation":{"name":"Needs automation","description":"Issues that needs automated tests","color":""},"Prepared statements":{"name":"Prepared statements","description":"Issues related to prepared statement flow","color":""},"Switch Group Widget":{"name":"Switch Group Widget","description":"Issues related to Switch group Widget","color":""},"Supervisor":{"name":"Supervisor","description":"Issues related to supervisor","color":"2c5813"},"Deployment Certificates":{"name":"Deployment Certificates","description":"Issues related to lets encrypt","color":"e148aa"},"Mock Data":{"name":"Mock Data","description":"Issues related to mock databases","color":"ebf251"},"AWS ECS":{"name":"AWS ECS","description":"Issues related to ECS Fargate","color":"e506ff"},"Publish App":{"name":"Publish App","description":"Issues related to app deployment","color":""},"IDE Infra":{"name":"IDE Infra","description":"Issues related to the IDE infrastructure like saving changes","color":"4c1858"},"User Profile":{"name":"User Profile","description":"Issues related to a user profile","color":"a60d34"},"Admin Settings":{"color":"32a316","name":"Admin Settings","description":"Issues related to admin settings"},"Workspace settings":{"name":"Workspace settings","description":"Issues related to workspace settings","color":"47d1ad"},"Page Management":{"color":"e17a68","name":"Page Management","description":"Issues related to configuring pages"},"Test":{"name":"Test","description":"","color":"33515b"},"Ingress":{"name":"Ingress","description":"Ingress Controller","color":"a86802"},"Nginx":{"name":"Nginx","description":"Issues related to Nginx","color":"e54195"},"Workflows":{"name":"Workflows","description":"","color":"1b89db"},"Building blocks":{"name":"Building blocks","description":"Building blocks on cavas, on templates listing or drag and drop of building blocks.","color":"8e3c7a"},"Widget design system POD":{"name":"Widget design system POD","description":"","color":"bbeecd"},"Table Inline Edit":{"name":"Table Inline Edit","description":"Issues related to inline editing","color":"60895a"}},"success":true} \ No newline at end of file diff --git a/app/client/cypress/e2e/Regression/ClientSide/Binding/Input_NavigateTo_validation_spec.js b/app/client/cypress/e2e/Regression/ClientSide/Binding/Input_NavigateTo_validation_spec.js index f66a1addb4..d9dc2b6aaf 100644 --- a/app/client/cypress/e2e/Regression/ClientSide/Binding/Input_NavigateTo_validation_spec.js +++ b/app/client/cypress/e2e/Regression/ClientSide/Binding/Input_NavigateTo_validation_spec.js @@ -11,6 +11,7 @@ const publish = require("../../../../locators/publishWidgetspage.json"); const testdata = require("../../../../fixtures/testdata.json"); const pageid = "MyPage"; import { agHelper, propPane } from "../../../../support/Objects/ObjectsCore"; +import PageList from "../../../../support/Pages/PageList"; describe( "Binding the multiple Widgets and validating NavigateTo Page", @@ -33,7 +34,7 @@ describe( agHelper.AddDsl("displayWidgetDsl"); // eslint-disable-next-line cypress/no-unnecessary-waiting cy.wait(3000); - cy.CheckAndUnfoldEntityItem("Pages"); + PageList.ShowList(); PageLeftPane.assertPresence(pageid); }); diff --git a/app/client/cypress/e2e/Regression/ClientSide/Binding/TableV2Widgets_NavigateTo_Validation_spec.js b/app/client/cypress/e2e/Regression/ClientSide/Binding/TableV2Widgets_NavigateTo_Validation_spec.js index 06f9acb0ba..3e1fd59a7e 100644 --- a/app/client/cypress/e2e/Regression/ClientSide/Binding/TableV2Widgets_NavigateTo_Validation_spec.js +++ b/app/client/cypress/e2e/Regression/ClientSide/Binding/TableV2Widgets_NavigateTo_Validation_spec.js @@ -12,6 +12,7 @@ import { propPane, deployMode, } from "../../../../support/Objects/ObjectsCore"; +import PageList from "../../../../support/Pages/PageList"; describe( "Table Widget V2 and Navigate to functionality validation", @@ -34,7 +35,7 @@ describe( agHelper.AddDsl("displayWidgetDsl"); // eslint-disable-next-line cypress/no-unnecessary-waiting cy.wait(500); - PageLeftPane.expandCollapseItem("Pages"); + PageList.ShowList(); PageLeftPane.assertPresence(pageid); //Table Widget V2 Functionality with multiple page EditorNavigation.SelectEntityByName("Page1", EntityType.Page); diff --git a/app/client/cypress/e2e/Regression/ClientSide/ExplorerTests/Hide_Page_spec.js b/app/client/cypress/e2e/Regression/ClientSide/ExplorerTests/Hide_Page_spec.js index a3ae877c73..1b44f3d403 100644 --- a/app/client/cypress/e2e/Regression/ClientSide/ExplorerTests/Hide_Page_spec.js +++ b/app/client/cypress/e2e/Regression/ClientSide/ExplorerTests/Hide_Page_spec.js @@ -4,14 +4,15 @@ import EditorNavigation, { } from "../../../../support/Pages/EditorNavigation"; import * as _ from "../../../../support/Objects/ObjectsCore"; +import PageList from "../../../../support/Pages/PageList"; describe( "Hide / Show page test functionality", { tags: ["@tag.IDE"] }, function () { it("1. Hide/Show page test ", function () { - cy.CreatePage(); // Page2 - cy.CreatePage(); // Page3 + PageList.AddNewPage(); // Page2 + PageList.AddNewPage(); // Page3 EditorNavigation.SelectEntityByName("Page1", EntityType.Page); _.entityExplorer.ActionContextMenuByEntityName({ entityNameinLeftSidebar: "Page2", diff --git a/app/client/cypress/e2e/Regression/ClientSide/ExplorerTests/Page_Load_Spec.js b/app/client/cypress/e2e/Regression/ClientSide/ExplorerTests/Page_Load_Spec.js index 2dfc825e2e..20a2a94ac4 100644 --- a/app/client/cypress/e2e/Regression/ClientSide/ExplorerTests/Page_Load_Spec.js +++ b/app/client/cypress/e2e/Regression/ClientSide/ExplorerTests/Page_Load_Spec.js @@ -8,6 +8,7 @@ import { deployMode, entityExplorer, } from "../../../../support/Objects/ObjectsCore"; +import PageList from "../../../../support/Pages/PageList"; describe("Page Load tests", { tags: ["@tag.IDE"] }, () => { afterEach(() => { @@ -20,7 +21,7 @@ describe("Page Load tests", { tags: ["@tag.IDE"] }, () => { before(() => { agHelper.AddDsl("PageLoadDsl"); - cy.CreatePage(); + PageList.AddNewPage(); cy.get("h2").contains("Drag and drop a widget here"); }); diff --git a/app/client/cypress/e2e/Regression/ClientSide/Git/GitDiscardChange/DiscardChanges_spec.js b/app/client/cypress/e2e/Regression/ClientSide/Git/GitDiscardChange/DiscardChanges_spec.js index cfe385209d..bbeeb4f187 100644 --- a/app/client/cypress/e2e/Regression/ClientSide/Git/GitDiscardChange/DiscardChanges_spec.js +++ b/app/client/cypress/e2e/Regression/ClientSide/Git/GitDiscardChange/DiscardChanges_spec.js @@ -95,7 +95,7 @@ describe("Git discard changes:", { tags: ["@tag.Git"] }, function () { }); it("4. Delete page2 and trigger discard flow, page2 should be available again", () => { - cy.Deletepage(page2); + PageList.DeletePage(page2); // verify page is deleted //entityExplorer.ExpandCollapseEntity("Pages"); PageLeftPane.assertAbsence(page2); @@ -161,7 +161,7 @@ describe("Git discard changes:", { tags: ["@tag.Git"] }, function () { // discard changes gitSync.DiscardChanges(); // verify page3 is removed - PageLeftPane.expandCollapseItem("Pages"); + PageList.ShowList(); PageLeftPane.assertAbsence(page3); }); diff --git a/app/client/cypress/e2e/Regression/ClientSide/Git/GitSync/GitBugs_spec.js b/app/client/cypress/e2e/Regression/ClientSide/Git/GitSync/GitBugs_spec.js index c196f5065a..637c496acc 100644 --- a/app/client/cypress/e2e/Regression/ClientSide/Git/GitSync/GitBugs_spec.js +++ b/app/client/cypress/e2e/Regression/ClientSide/Git/GitSync/GitBugs_spec.js @@ -15,6 +15,7 @@ import EditorNavigation, { PageLeftPane, PagePaneSegment, } from "../../../../../support/Pages/EditorNavigation"; +import PageList from "../../../../../support/Pages/PageList"; const pagename = "ChildPage"; const tempBranch = "feat/tempBranch"; @@ -48,11 +49,10 @@ describe("Git sync Bug #10773", { tags: ["@tag.Git"] }, function () { cy.wait(2000); gitSync.CreateGitBranch(tempBranch, false); //cy.createGitBranch(tempBranch); - cy.CheckAndUnfoldEntityItem("Pages"); // verify tempBranch should contain this page EditorNavigation.SelectEntityByName(pagename, EntityType.Page); // delete page from tempBranch and merge to master - cy.Deletepage(pagename); + PageList.DeletePage(pagename); cy.get(homePageLocators.publishButton).click(); cy.get(gitSyncLocators.commitCommentInput).type("Initial Commit"); cy.get(gitSyncLocators.commitButton).click(); @@ -62,12 +62,12 @@ describe("Git sync Bug #10773", { tags: ["@tag.Git"] }, function () { cy.get(gitSyncLocators.closeGitSyncModal).click(); // verify ChildPage is not on master cy.switchGitBranch(mainBranch); - PageLeftPane.expandCollapseItem("Pages"); + PageList.ShowList(); PageLeftPane.assertAbsence(pagename); // create another branch and verify deleted page doesn't exist on it //cy.createGitBranch(tempBranch0); gitSync.CreateGitBranch(tempBranch0, false); - PageLeftPane.expandCollapseItem("Pages"); + PageList.ShowList(); PageLeftPane.assertAbsence(pagename); gitSync.DeleteTestGithubRepo(repoName); }); diff --git a/app/client/cypress/e2e/Regression/ClientSide/Git/GitSync/GitSyncedApps_spec.js b/app/client/cypress/e2e/Regression/ClientSide/Git/GitSync/GitSyncedApps_spec.js index a52efcabdf..804f24f784 100644 --- a/app/client/cypress/e2e/Regression/ClientSide/Git/GitSync/GitSyncedApps_spec.js +++ b/app/client/cypress/e2e/Regression/ClientSide/Git/GitSync/GitSyncedApps_spec.js @@ -277,7 +277,6 @@ describe("Git sync apps", { tags: ["@tag.Git"] }, function () { ); dataSources.RunQuery(); // create a new page - cy.CheckAndUnfoldEntityItem("Pages"); cy.Createpage("Child_Page"); EditorNavigation.SelectEntityByName(`${newPage} Copy`, EntityType.Page); EditorNavigation.SelectEntityByName("get_users", EntityType.Query); @@ -459,7 +458,7 @@ describe("Git sync apps", { tags: ["@tag.Git"] }, function () { // delete page from page settings EditorNavigation.SelectEntityByName("Child_Page Copy", EntityType.Page); cy.wait("@getConsolidatedData"); - cy.Deletepage("Child_Page Copy"); + PageList.DeletePage("Child_Page Copy"); cy.get(homePageLocators.publishButton).click(); cy.get(gitSyncLocators.commitCommentInput).type("Initial Commit"); cy.get(gitSyncLocators.commitButton).click(); @@ -482,11 +481,11 @@ describe("Git sync apps", { tags: ["@tag.Git"] }, function () { expect(cellData).to.be.equal("New Config"); }); agHelper.AssertAutoSave(); - PageLeftPane.expandCollapseItem("Pages"); + PageList.ShowList(); PageLeftPane.assertAbsence("Child_Page Copy"); // create another branch and verify deleted page doesn't exist on it gitSync.CreateGitBranch(tempBranch0, true); - PageLeftPane.expandCollapseItem("Pages"); + PageList.ShowList(); PageLeftPane.assertAbsence("Child_Page Copy"); }); @@ -498,7 +497,7 @@ describe("Git sync apps", { tags: ["@tag.Git"] }, function () { // import application from git cy.importAppFromGit(repoName); // verify page order remains same as in orignal app - cy.CheckAndUnfoldEntityItem("Pages"); + PageList.ShowList(); cy.get(".t--entity-item").eq(1).contains("crudpage_1"); cy.get(".t--entity-item").eq(2).contains("crudpage_1 Copy"); cy.get(".t--entity-item").eq(3).contains("ApiCalls_1"); diff --git a/app/client/cypress/e2e/Regression/ClientSide/Git/GitSync/MergeViaRemote_spec.ts b/app/client/cypress/e2e/Regression/ClientSide/Git/GitSync/MergeViaRemote_spec.ts index 1a5a748d6d..4f7e10a9d0 100644 --- a/app/client/cypress/e2e/Regression/ClientSide/Git/GitSync/MergeViaRemote_spec.ts +++ b/app/client/cypress/e2e/Regression/ClientSide/Git/GitSync/MergeViaRemote_spec.ts @@ -1,12 +1,10 @@ -import widgetsPage from "../../../../../locators/Widgets.json"; -import commonlocators from "../../../../../locators/commonlocators.json"; import gitSyncLocators from "../../../../../locators/gitSyncLocators"; -import homePage from "../../../../../locators/HomePage"; import * as _ from "../../../../../support/Objects/ObjectsCore"; import { PageLeftPane, PagePaneSegment, } from "../../../../../support/Pages/EditorNavigation"; +import PageList from "../../../../../support/Pages/PageList"; let tempBranch = "tempBranch", tempBranch0 = "tempBranch0", @@ -57,7 +55,6 @@ describe( //cy.switchGitBranch(mainBranch); _.gitSync.CreateGitBranch(tempBranch2, true); PageLeftPane.switchSegment(PagePaneSegment.UI); - cy.CheckAndUnfoldEntityItem("Pages"); cy.Createpage("NewPage"); cy.commitAndPush(); cy.merge(mainBranch); @@ -79,7 +76,7 @@ describe( }); it("3. Checks clean url updates across branches", () => { - cy.Deletepage("NewPage"); + PageList.DeletePage("NewPage"); cy.wait(1000); let legacyPathname = ""; let newPathname = ""; diff --git a/app/client/cypress/e2e/Regression/ClientSide/Git/GitSync/SwitchBranches_spec.js b/app/client/cypress/e2e/Regression/ClientSide/Git/GitSync/SwitchBranches_spec.js index 24a2b8d88b..ef1ca01853 100644 --- a/app/client/cypress/e2e/Regression/ClientSide/Git/GitSync/SwitchBranches_spec.js +++ b/app/client/cypress/e2e/Regression/ClientSide/Git/GitSync/SwitchBranches_spec.js @@ -121,7 +121,7 @@ describe("Git sync:", { tags: ["@tag.Git"] }, function () { cy.switchGitBranch(parentBranchKey); - PageLeftPane.expandCollapseItem("Pages"); + PageList.ShowList(); PageLeftPane.assertAbsence("ParentPageRenamed"); PageLeftPane.switchSegment(PagePaneSegment.Queries); PageLeftPane.assertAbsence("ParentApiRenamed"); @@ -212,7 +212,6 @@ describe("Git sync:", { tags: ["@tag.Git"] }, function () { cy.generateUUID().then((uuid) => { gitSync.CreateGitBranch(childBranchKey, true); //cy.createGitBranch(childBranchKey); - cy.CheckAndUnfoldEntityItem("Pages"); PageList.AddNewPage(); cy.get(gitSyncLocators.branchButton).click({ force: true }); cy.get(gitSyncLocators.branchSearchInput).type("{selectall}master"); diff --git a/app/client/cypress/e2e/Regression/ClientSide/OtherUIFeatures/DynamicLayout_spec.js b/app/client/cypress/e2e/Regression/ClientSide/OtherUIFeatures/DynamicLayout_spec.js index 7b3fc5763c..6722ab8527 100644 --- a/app/client/cypress/e2e/Regression/ClientSide/OtherUIFeatures/DynamicLayout_spec.js +++ b/app/client/cypress/e2e/Regression/ClientSide/OtherUIFeatures/DynamicLayout_spec.js @@ -1,5 +1,5 @@ const commonlocators = require("../../../../locators/commonlocators.json"); -const pages = require("../../../../locators/Pages.json"); +import PageList from "../../../../support/Pages/PageList"; describe("Dynamic Layout Functionality", function () { it("1. Dynamic Layout - Change Layout", function () { @@ -7,7 +7,7 @@ describe("Dynamic Layout Functionality", function () { cy.get(commonlocators.canvas).invoke("width").should("be.eq", 450); //Dynamic Layout - New Page should have selected Layout - cy.get(pages.AddPage).first().click(); + PageList.AddNewPage(); cy.get(commonlocators.canvas).invoke("width").should("be.eq", 450); }); }); diff --git a/app/client/cypress/e2e/Regression/ClientSide/ThemingTests/Basic_spec.js b/app/client/cypress/e2e/Regression/ClientSide/ThemingTests/Basic_spec.js index a7848fc963..e62d1ec529 100644 --- a/app/client/cypress/e2e/Regression/ClientSide/ThemingTests/Basic_spec.js +++ b/app/client/cypress/e2e/Regression/ClientSide/ThemingTests/Basic_spec.js @@ -167,247 +167,15 @@ describe("App Theming funtionality", { tags: ["@tag.Theme"] }, function () { }); }); - it("3. Checks if the theme can be saved", () => { - //Click on dropDown elipses - cy.contains("Theme properties") - .closest("div") - .siblings() - .first() - .find("button") - .click({ force: true }); - - agHelper.AssertAutoSave(); - - //Click on save theme dropdown option - cy.contains("Save theme").click({ force: true }); - - //Type the name of the theme: - agHelper.TypeText("input[placeholder='My theme']", "testtheme"); - //Click on save theme button - agHelper.ClickButton("Save theme"); - agHelper.ValidateToastMessage("Theme testtheme saved"); - appSettings.ClosePane(); - }); - - it("4. Verify Save Theme after changing all properties & widgets conform to the selected theme", () => { - cy.dragAndDropToCanvas("iconbuttonwidget", { x: 300, y: 300 }); - cy.assertPageSave(); - cy.get("canvas").first(0).trigger("click", { force: true }); - - appSettings.OpenAppSettings(); - appSettings.GoToThemeSettings(); - //#region Change Font & verify widgets: - - agHelper.GetNClick(".rc-select-selection-search-input").then(($elem) => { - cy.get($elem).click({ force: true }); - cy.wait(250); - cy.get(".rc-virtual-list-holder div") - .children() - .eq(4) - .then(($childElem) => { - cy.get($childElem).click({ force: true }); - cy.get(widgetsPage.iconWidgetBtn).should( - "have.css", - "font-family", - `${$childElem.children().last().text()}Inter, sans-serif`, - ); - cy.get(widgetsPage.widgetBtn).should( - "have.css", - "font-family", - `${$childElem.children().last().text()}Inter, sans-serif`, - ); - }); - }); - - cy.get(widgetsPage.colorPickerV2Popover).click({ force: true }).click(); - cy.get(widgetsPage.colorPickerV2Color) - .eq(-15) - .then(($elem) => { - cy.get($elem).click({ force: true }); - cy.get(widgetsPage.iconWidgetBtn).should( - "have.css", - "background-color", - $elem.css("background-color"), - ); - cy.get(widgetsPage.widgetBtn).should( - "have.css", - "background-color", - $elem.css("background-color"), - ); - }); - - //Change the background color: - cy.get("[data-testid='theme-backgroundColor']").click({ force: true }); - cy.wait(500); - cy.get(widgetsPage.colorPickerV2Popover).click({ force: true }).click(); - cy.get(widgetsPage.colorPickerV2TailwindColor) - .eq(23) - .then(($elem) => { - cy.get($elem).click({ force: true }); - cy.get(commonlocators.canvas).should( - "have.css", - "background-color", - $elem.css("background-color"), - ); - }); - - cy.get(commonlocators.themeAppBorderRadiusBtn).eq(2).click({ force: true }); - cy.get(`${commonlocators.themeAppBorderRadiusBtn}`) - .eq(2) - .invoke("css", "border-top-left-radius") - .then((borderRadius) => { - cy.get(widgetsPage.iconWidgetBtn).should( - "have.css", - "border-radius", - borderRadius, - ); - cy.get(widgetsPage.widgetBtn).should( - "have.css", - "border-radius", - borderRadius, - ); - }); - - //#region Change the shadow & verify widgets - cy.get("[data-value='L']").eq(1).click({ force: true }); - cy.get("[data-value='L']") - .eq(1) - .invoke("css", "box-shadow") - .then((boxShadow) => { - cy.get(containerShadowElement).should( - "have.css", - "box-shadow", - boxShadow, - ); - }); - - //#region Click on dropDown elipses - cy.contains("Theme properties") - .closest("div") - .siblings() - .first() - .find("button") - .click({ force: true }); - cy.wait(300); - - //Click on save theme dropdown option & close it - cy.contains("Save theme").click({ force: true }); - cy.wait(200); - cy.get(".ads-v2-modal__content-header-close-button").click(); - - //Click on save theme dropdown option & cancel it - cy.contains("Theme properties") - .closest("div") - .siblings() - .first() - .find("button") - .click({ force: true }); - cy.wait(300); - cy.contains("Save theme").click({ force: true }); - cy.wait(200); - cy.xpath("//span[text()='Cancel']/parent::div").click(); - - //Click on save theme dropdown option, give duplicte name & save it - cy.contains("Theme properties") - .closest("div") - .siblings() - .first() - .find("button") - .click({ force: true }); - cy.wait(300); - cy.contains("Save theme").click({ force: true }); - cy.wait(200); - //Type the name of the theme: - agHelper.TypeText("input[placeholder='My theme']", "testtheme"); - cy.contains("Name must be unique"); - - cy.get("input[placeholder='My theme']").clear().type("VioletYellowTheme"); - - //Click on save theme button - agHelper.ClickButton("Save theme"); - agHelper.ValidateToastMessage("Theme VioletYellowTheme saved"); - }); - - it("5. Verify Themes exists under respective section when ChangeTheme button is cicked in properties with Apply Theme & Trash as applicable", () => { - //Click on change theme: + it("4. Verify user able to change between saved theme & already existing Featured themes", () => { cy.get(commonlocators.changeThemeBtn).click({ force: true }); - cy.xpath(applyTheme("Your themes", "testtheme")) - .click({ force: true }) - .wait(1000); //Changing to testtheme - cy.contains("Applied theme") - .click() - .parent() - .siblings() - .find(".t--theme-card > main > main") - .invoke("css", "background-color") - .then((backgroudColor) => { - expect(backgroudColor).to.eq("rgb(236, 72, 153)"); - }); - - //Check if the saved theme is present under 'Yours Themes' section with Trash button - cy.xpath(applyTheme("Your themes", "testtheme")).should("exist"); - cy.xpath(themesDeletebtn("Your themes", "testtheme")).should("exist"); - - cy.xpath(applyTheme("Your themes", "VioletYellowTheme")).should("exist"); - cy.xpath(themesDeletebtn("Your themes", "VioletYellowTheme")).should( - "exist", - ); - - cy.xpath(applyTheme("Featured themes", "Earth")).should("exist"); - cy.xpath(themesDeletebtn("Featured themes", "Earth")).should("not.exist"); - - cy.xpath(applyTheme("Featured themes", "Sunrise")).should("exist"); - cy.xpath(themesDeletebtn("Featured themes", "Sunrise")).should("not.exist"); - - cy.xpath(applyTheme("Featured themes", "Pacific")).should("exist"); - cy.xpath(themesDeletebtn("Featured themes", "Pacific")).should("not.exist"); - - cy.xpath(applyTheme("Featured themes", "Pampas")).should("exist"); - cy.xpath(themesDeletebtn("Featured themes", "Pampas")).should("not.exist"); - }); - - it("6. Verify the custom theme can be deleted", () => { - //Delete the created theme - cy.xpath(themesDeletebtn("Your themes", "testtheme")) - .click({ force: true }) - .wait(200); - cy.contains( - "Do you really want to delete this theme? This process cannot be undone.", - ); - - //Click on Delete theme trash icon & close it - cy.xpath("//*[text()='Are you sure?']/following-sibling::button").click(); - cy.get(commonlocators.toastMsg).should("not.exist"); - - //Click on Delete theme trash icon & cancel it - cy.xpath(themesDeletebtn("Your themes", "testtheme")) - .click({ force: true }) - .wait(200); - cy.xpath("//span[text()='No']/parent::div").click(); - cy.get(commonlocators.toastMsg).should("not.exist"); - - //Click on Delete theme trash icon & delete it - cy.xpath(themesDeletebtn("Your themes", "testtheme")) - .click({ force: true }) - .wait(200); - agHelper.ClickButton("Delete"); - // cy.contains("Delete").click({ force: true }); - - //check for delete alert - // cy.wait(500); - agHelper.ValidateToastMessage("Theme testtheme deleted"); - //cy.get(commonlocators.toastMsg).contains("Theme testtheme deleted"); - cy.xpath(applyTheme("Your themes", "testtheme")).should("not.exist"); - }); - - it("7. Verify user able to change between saved theme & already existing Featured themes", () => { //#region Pampas cy.xpath(applyTheme("Featured themes", "Pampas")) .click({ force: true }) .wait(1000); //Changing to one of Featured themes cy.contains("Applied theme") - // .click() + .click() .parent() .siblings() .find(".t--theme-card > main > section > div > main") @@ -620,70 +388,38 @@ describe("App Theming funtionality", { tags: ["@tag.Theme"] }, function () { expect(backgroudColor).to.eq("rgb(248, 250, 252)"); }); //#endregion - - //#region VioletYellowTheme - cy.xpath(applyTheme("Your themes", "VioletYellowTheme")) - .click({ force: true }) - .wait(1000); //Changing to created test theme - - cy.contains("Applied theme") - // .click() - .parent() - .siblings() - .find(".t--theme-card > main > section > div > main") - .eq(0) - .invoke("css", "background-color") - .then((backgroudColor) => { - expect(backgroudColor).to.eq("rgb(219, 234, 254)"); - }); - - cy.contains("Applied theme") - // .click() - .parent() - .siblings() - .find(".t--theme-card > main > section > div > main") - .eq(1) - .invoke("css", "background-color") - .then((backgroudColor) => { - expect(backgroudColor).to.eq("rgb(29, 78, 216)"); - }); - - //#endregion }); - it("8. Verify widgets conform to the selected theme in Publish mode", () => { + it("5. Verify widgets conform to the selected theme in Publish mode", () => { deployMode.DeployApp(); //cy.wait(4000); //for theme to settle - cy.get("body").should("have.css", "font-family", "Inter, sans-serif"); //Font + cy.get("body").should( + "have.css", + "font-family", + `"Nunito Sans", sans-serif`, + ); //Font cy.xpath("//div[@id='root']//section/parent::div").should( "have.css", "background-color", - "rgb(29, 78, 216)", + "rgb(248, 250, 252)", ); //Background Color cy.get(widgetsPage.widgetBtn).should( "have.css", "background-color", - "rgb(219, 234, 254)", - ); //Widget Color - cy.get(publish.iconWidgetBtn).should( - "have.css", - "background-color", - "rgb(219, 234, 254)", + "rgb(100, 116, 139)", ); //Widget Color - cy.get(widgetsPage.widgetBtn).should("have.css", "border-radius", "24px"); //Border Radius - cy.get(publish.iconWidgetBtn).should("have.css", "border-radius", "24px"); //Border Radius + cy.get(widgetsPage.widgetBtn).should("have.css", "border-radius", "0px"); //Border Radius cy.get(widgetsPage.widgetBtn).should("have.css", "box-shadow", "none"); //Shadow - cy.get(publish.iconWidgetBtn).should("have.css", "box-shadow", "none"); //Shadow deployMode.NavigateBacktoEditor(); }); - it("9. Verify Adding new Individual widgets & it can change Color, Border radius, Shadow & can revert [Color/Border Radius] to already selected theme", () => { + it("6. Verify Adding new Individual widgets & it can change Color, Border radius, Shadow & can revert [Color/Border Radius] to already selected theme", () => { cy.dragAndDropToCanvas("buttonwidget", { x: 200, y: 400 }); //another button widget cy.moveToStyleTab(); //Change Color & verify @@ -701,13 +437,8 @@ describe("App Theming funtionality", { tags: ["@tag.Theme"] }, function () { cy.get(".t--widget-button1 button").should( "have.css", "background-color", - "rgb(219, 234, 254)", + "rgb(100, 116, 139)", ); //old widgets still conforming to theme color - cy.get(widgetsPage.iconWidgetBtn).should( - "have.css", - "background-color", - "rgb(219, 234, 254)", - ); }); //Change Border & verify @@ -722,22 +453,16 @@ describe("App Theming funtionality", { tags: ["@tag.Theme"] }, function () { "border-radius", borderRadius, //0px ); - cy.get(widgetsPage.iconWidgetBtn).should( - "have.css", - "border-radius", - "24px", - ); cy.get(".t--widget-button1 button").should( "have.css", "border-radius", - "24px", + "0px", ); }); //Change Shadow & verify cy.contains(".ads-v2-segmented-control-value-0", "Large").click(); - cy.get(widgetsPage.iconWidgetBtn).should("have.css", "box-shadow", "none"); cy.get(".t--widget-button1 button").should( "have.css", "box-shadow", @@ -748,23 +473,17 @@ describe("App Theming funtionality", { tags: ["@tag.Theme"] }, function () { deployMode.DeployApp(); //Verify Background color - cy.get(".t--widget-buttonwidget:nth-child(4) button").should( + cy.get(".t--widget-button2 button").should( "have.css", "background-color", "rgb(190, 24, 93)", ); //new widget with its own color ////old widgets still conforming to theme color - cy.get(".t--widget-buttonwidget button").should( + cy.get(".t--widget-button1 button").should( "have.css", "background-color", - "rgb(219, 234, 254)", - ); - - cy.get(publish.iconWidgetBtn).should( - "have.css", - "background-color", - "rgb(219, 234, 254)", + "rgb(100, 116, 139)", ); //Verify Border radius @@ -773,11 +492,10 @@ describe("App Theming funtionality", { tags: ["@tag.Theme"] }, function () { "border-radius", "0px", ); - cy.get(publish.iconWidgetBtn).should("have.css", "border-radius", "24px"); cy.get(".t--widget-button1 button").should( "have.css", "border-radius", - "24px", + "0px", ); //Verify Box shadow @@ -786,7 +504,6 @@ describe("App Theming funtionality", { tags: ["@tag.Theme"] }, function () { "box-shadow", "rgba(0, 0, 0, 0.1) 0px 10px 15px -3px, rgba(0, 0, 0, 0.05) 0px 4px 6px -2px", ); - cy.get(publish.iconWidgetBtn).should("have.css", "box-shadow", "none"); cy.get(".t--widget-button1 button").should( "have.css", "box-shadow", @@ -805,7 +522,7 @@ describe("App Theming funtionality", { tags: ["@tag.Theme"] }, function () { cy.get(".t--widget-button2 button").should( "have.css", "background-color", - "rgb(219, 234, 254)", + "rgb(100, 116, 139)", ); //verify widget reverted to theme color cy.get(".t--property-control-borderradius .reset-button").then(($elem) => { $elem[0].removeAttribute("display: none"); @@ -814,24 +531,28 @@ describe("App Theming funtionality", { tags: ["@tag.Theme"] }, function () { cy.get(".t--widget-button2 button").should( "have.css", "border-radius", - "24px", + "0px", ); //the new widget with reverted styles also conforming to theme deployMode.DeployApp(); cy.wait(4000); //for theme to settle - cy.get("body").should("have.css", "font-family", "Inter, sans-serif"); //Font + cy.get("body").should( + "have.css", + "font-family", + `"Nunito Sans", sans-serif`, + ); //Font cy.xpath("//div[@id='root']//section/parent::div").should( "have.css", "background-color", - "rgb(29, 78, 216)", + "rgb(248, 250, 252)", ); //Background Color cy.get(".t--widget-button1 button").should( "have.css", "background-color", - "rgb(219, 234, 254)", + "rgb(100, 116, 139)", ); //Widget Color cy.get("body").then(($ele) => { if ($ele.find(widgetsPage.widgetBtn).length <= 1) { @@ -842,25 +563,19 @@ describe("App Theming funtionality", { tags: ["@tag.Theme"] }, function () { cy.get(".t--widget-button2 button").should( "have.css", "background-color", - "rgb(219, 234, 254)", - ); //Widget Color - cy.get(publish.iconWidgetBtn).should( - "have.css", - "background-color", - "rgb(219, 234, 254)", + "rgb(100, 116, 139)", ); //Widget Color cy.get(".t--widget-button1 button").should( "have.css", "border-radius", - "24px", + "0px", ); //Border Radius cy.get(".t--widget-button2 button").should( "have.css", "border-radius", - "24px", + "0px", ); //Border Radius - cy.get(publish.iconWidgetBtn).should("have.css", "border-radius", "24px"); //Border Radius cy.get(".t--widget-button1 button").should( "have.css", @@ -872,12 +587,10 @@ describe("App Theming funtionality", { tags: ["@tag.Theme"] }, function () { "box-shadow", "rgba(0, 0, 0, 0.1) 0px 10px 15px -3px, rgba(0, 0, 0, 0.05) 0px 4px 6px -2px", ); //Since Shadow revert option does not exixts - cy.get(publish.iconWidgetBtn).should("have.css", "box-shadow", "none"); //Shadow - deployMode.NavigateBacktoEditor(); }); - it("10. Verify Chainging theme should not affect Individual widgets with changed Color, Border radius, Shadow & can revert to newly selected theme", () => { + it("7. Verify Chainging theme should not affect Individual widgets with changed Color, Border radius, Shadow & can revert to newly selected theme", () => { cy.get("canvas").first(0).trigger("click", { force: true }); appSettings.OpenAppSettings(); @@ -911,11 +624,6 @@ describe("App Theming funtionality", { tags: ["@tag.Theme"] }, function () { "background-color", "rgb(239, 68, 68)", ); //old widgets still conforming to theme color - cy.get(widgetsPage.iconWidgetBtn).should( - "have.css", - "background-color", - "rgb(239, 68, 68)", - ); }); //Change Border & verify @@ -930,11 +638,7 @@ describe("App Theming funtionality", { tags: ["@tag.Theme"] }, function () { "border-radius", borderRadius, //6px ); - cy.get(widgetsPage.iconWidgetBtn).should( - "have.css", - "border-radius", - "24px", - ); + cy.get(".t--widget-button2 button").should( "have.css", "border-radius", @@ -944,7 +648,6 @@ describe("App Theming funtionality", { tags: ["@tag.Theme"] }, function () { //Change Shadow & verify cy.contains(".ads-v2-segmented-control-value-0", "Small").click(); - cy.get(widgetsPage.iconWidgetBtn).should("have.css", "box-shadow", "none"); cy.get(".t--widget-button2 button").should( "have.css", "box-shadow", @@ -971,11 +674,6 @@ describe("App Theming funtionality", { tags: ["@tag.Theme"] }, function () { "background-color", "rgb(239, 68, 68)", ); - cy.get(publish.iconWidgetBtn).should( - "have.css", - "background-color", - "rgb(239, 68, 68)", - ); //Verify Border radius cy.get(".t--widget-button1 button").should( @@ -983,7 +681,6 @@ describe("App Theming funtionality", { tags: ["@tag.Theme"] }, function () { "border-radius", "6px", ); - cy.get(publish.iconWidgetBtn).should("have.css", "border-radius", "24px"); cy.get(".t--widget-button2 button").should( "have.css", "border-radius", @@ -996,7 +693,6 @@ describe("App Theming funtionality", { tags: ["@tag.Theme"] }, function () { "box-shadow", "rgba(0, 0, 0, 0.1) 0px 1px 3px 0px, rgba(0, 0, 0, 0.06) 0px 1px 2px 0px", ); - cy.get(publish.iconWidgetBtn).should("have.css", "box-shadow", "none"); cy.get(".t--widget-button2 button").should( "have.css", "box-shadow", @@ -1056,11 +752,6 @@ describe("App Theming funtionality", { tags: ["@tag.Theme"] }, function () { "background-color", "rgb(239, 68, 68)", ); //Widget Color - cy.get(publish.iconWidgetBtn).should( - "have.css", - "background-color", - "rgb(239, 68, 68)", - ); //Widget Color cy.get(".t--widget-button1 button").should( "have.css", @@ -1072,7 +763,6 @@ describe("App Theming funtionality", { tags: ["@tag.Theme"] }, function () { "border-radius", "24px", ); //Border Radius - cy.get(publish.iconWidgetBtn).should("have.css", "border-radius", "24px"); //Border Radius cy.get(".t--widget-button1 button").should( "have.css", @@ -1084,7 +774,6 @@ describe("App Theming funtionality", { tags: ["@tag.Theme"] }, function () { "box-shadow", "rgba(0, 0, 0, 0.1) 0px 10px 15px -3px, rgba(0, 0, 0, 0.05) 0px 4px 6px -2px", ); //Since Shadow revert option does not exixts - cy.get(publish.iconWidgetBtn).should("have.css", "box-shadow", "none"); //Shadow deployMode.NavigateBacktoEditor(); }); diff --git a/app/client/cypress/e2e/Regression/ClientSide/Widgets/ContainerTest2_spec.ts b/app/client/cypress/e2e/Regression/ClientSide/Widgets/ContainerTest2_spec.ts index 27c8963d7c..9045781906 100644 --- a/app/client/cypress/e2e/Regression/ClientSide/Widgets/ContainerTest2_spec.ts +++ b/app/client/cypress/e2e/Regression/ClientSide/Widgets/ContainerTest2_spec.ts @@ -5,7 +5,6 @@ import { locators, propPane, } from "../../../../support/Objects/ObjectsCore"; -import Canvas from "../../../../support/Pages/Canvas"; import EditorNavigation, { EntityType, PageLeftPane, @@ -94,12 +93,9 @@ describe( ); deployMode.NavigateBacktoEditor(); - // Verify multiple widgets selected groups into single container - Canvas.selectMultipleWidgets(["Input1", "Select1", "Text3"]); - agHelper.GetElement("body").type(`{${agHelper._modifierKey}}{g}`); - agHelper.Sleep(1000); - PageLeftPane.assertPresence("Container3"); - entityExplorer.DeleteWidgetFromEntityExplorer("Container3"); + entityExplorer.DeleteWidgetFromEntityExplorer("Input1"); + entityExplorer.DeleteWidgetFromEntityExplorer("Select1"); + entityExplorer.DeleteWidgetFromEntityExplorer("Text3"); }); it("4. Validate visible toggle", () => { diff --git a/app/client/cypress/e2e/Regression/ClientSide/Widgets/CurrencyInput/CurrencyInput_spec.js b/app/client/cypress/e2e/Regression/ClientSide/Widgets/CurrencyInput/CurrencyInput_spec.js index 221c984351..e9f9e34752 100644 --- a/app/client/cypress/e2e/Regression/ClientSide/Widgets/CurrencyInput/CurrencyInput_spec.js +++ b/app/client/cypress/e2e/Regression/ClientSide/Widgets/CurrencyInput/CurrencyInput_spec.js @@ -286,7 +286,7 @@ describe( //Should check that widget input is not showing any errors on input cy.get(widgetInput).type("123456789"); cy.focused().then(() => { - expect(Cypress.$(themelocators.popover)).not.to.exist; + cy.get(".error-tooltip .bp3-popover-content").should("not.exist"); }); }); }, diff --git a/app/client/cypress/e2e/Regression/ClientSide/Widgets/Iframe/Iframe_onSrcDocChange_spec.js b/app/client/cypress/e2e/Regression/ClientSide/Widgets/Iframe/Iframe_onSrcDocChange_spec.js index f788df7587..79a84b9f6a 100644 --- a/app/client/cypress/e2e/Regression/ClientSide/Widgets/Iframe/Iframe_onSrcDocChange_spec.js +++ b/app/client/cypress/e2e/Regression/ClientSide/Widgets/Iframe/Iframe_onSrcDocChange_spec.js @@ -1,3 +1,4 @@ +import PageList from "../../../../../support/Pages/PageList"; const { ObjectsRegistry } = require("../../../../../support/Objects/Registry"); import EditorNavigation, { EntityType, @@ -31,13 +32,14 @@ describe( it("2.Check the OnSrcDocChange event call on first render", () => { agHelper.RefreshPage(); cy.wait(2000); - cy.get(`.t--entity .page`).first().should("have.class", "activePage"); + PageList.ShowList(); + PageList.VerifyIsCurrentPage("Page1"); cy.openPropertyPane("iframewidget"); cy.testJsontext("srcdoc", "

Hello World!

"); cy.wait(2000); - cy.get(`.t--entity .page`).last().should("have.class", "activePage"); + PageList.VerifyIsCurrentPage("Page2"); EditorNavigation.SelectEntityByName(page1, EntityType.Page); - cy.get(`.t--entity .page`).first().should("have.class", "activePage"); + PageList.VerifyIsCurrentPage("Page1"); }); }, ); diff --git a/app/client/cypress/e2e/Regression/ClientSide/Widgets/ListV2/ListV2_NestedList_spec.ts b/app/client/cypress/e2e/Regression/ClientSide/Widgets/ListV2/ListV2_NestedList_spec.ts index 266064d28d..2ce68154fb 100644 --- a/app/client/cypress/e2e/Regression/ClientSide/Widgets/ListV2/ListV2_NestedList_spec.ts +++ b/app/client/cypress/e2e/Regression/ClientSide/Widgets/ListV2/ListV2_NestedList_spec.ts @@ -154,6 +154,7 @@ describe( it("5. Verify Theme change", () => { agHelper.PressEscape(); appSettings.OpenPaneAndChangeTheme("Pacific"); + agHelper.WaitUntilToastDisappear("Theme Pacific applied"); [0, 1, 2].forEach((index) => { agHelper.AssertAttribute( locators._listText, diff --git a/app/client/cypress/e2e/Regression/ClientSide/Widgets/ListV2/Listv2_BasicChildWidgetInteraction_spec.js b/app/client/cypress/e2e/Regression/ClientSide/Widgets/ListV2/Listv2_BasicChildWidgetInteraction_spec.js index bcd2f9ecd9..7b9fae85d3 100644 --- a/app/client/cypress/e2e/Regression/ClientSide/Widgets/ListV2/Listv2_BasicChildWidgetInteraction_spec.js +++ b/app/client/cypress/e2e/Regression/ClientSide/Widgets/ListV2/Listv2_BasicChildWidgetInteraction_spec.js @@ -11,6 +11,7 @@ const containerWidgetSelector = `[type="CONTAINER_WIDGET"]`; function dragAndDropToWidget(widgetType, destinationWidget, { x, y }) { const selector = `.t--widget-card-draggable-${widgetType}`; cy.wait(800); + PageLeftPane.switchToAddNew(); cy.get(selector) .first() .scrollIntoView() @@ -34,9 +35,9 @@ function deleteAllWidgetsInContainer() { force: true, }); cy.get("body").type(`{${modifierKey}}{a}`); - cy.get("body").type("{del}"); - cy.wait(200); + cy.get("body").type("{del}"); + cy.get(commonlocators.layoutControls).should("be.visible"); } function checkSelectedRadioValue(selector, value) { @@ -63,12 +64,13 @@ describe( x: 250, y: 50, }); + cy.assertPageSave(); // Verify drop cy.get(publishLocators.inputWidget).should("exist"); // Type value - cy.get(publishLocators.inputWidget).find("input").type("abcd"); + cy.get(publishLocators.inputWidget).find("input").first().type("abcd"); // Verify if the value got typed cy.get(publishLocators.inputWidget) @@ -78,7 +80,6 @@ describe( deleteAllWidgetsInContainer(); // Drop Select widget - PageLeftPane.switchToAddNew(); dragAndDropToWidget("selectwidget", "containerwidget", { x: 250, y: 50, @@ -115,7 +116,6 @@ describe( deleteAllWidgetsInContainer(); // Drop Checkbox widget - PageLeftPane.switchToAddNew(); dragAndDropToWidget("checkboxgroupwidget", "containerwidget", { x: 250, y: 50, @@ -158,7 +158,6 @@ describe( deleteAllWidgetsInContainer(); // Drop Switch widget - PageLeftPane.switchToAddNew(); dragAndDropToWidget("switchwidget", "containerwidget", { x: 250, y: 50, @@ -201,9 +200,8 @@ describe( _.deployMode.NavigateBacktoEditor(); deleteAllWidgetsInContainer(); - + cy.wait(800); // Drop Radio widget - PageLeftPane.switchToAddNew(); dragAndDropToWidget("radiogroupwidget", "containerwidget", { x: 250, y: 50, diff --git a/app/client/cypress/e2e/Regression/ClientSide/Widgets/ListV2/Listv2_spec.js b/app/client/cypress/e2e/Regression/ClientSide/Widgets/ListV2/Listv2_spec.js index 4b0c2e1f6b..afebdc4abf 100644 --- a/app/client/cypress/e2e/Regression/ClientSide/Widgets/ListV2/Listv2_spec.js +++ b/app/client/cypress/e2e/Regression/ClientSide/Widgets/ListV2/Listv2_spec.js @@ -68,7 +68,8 @@ describe( entityExplorer.DragDropWidgetNVerify(widget); //cy.dragAndDropToWidget(widget, "listwidgetv2", { x: 350, y: 50 }); agHelper.GetNClick(propPane._deleteWidget); - cy.wait("@updateLayout"); + cy.assertPageSave(); + cy.wait(800); }); }, ); @@ -88,7 +89,8 @@ describe( cy.assertPageSave(); cy.get(`.t--draggable-${widget}`).should("exist"); cy.get(widgetsPage.removeWidget).click({ force: true }); - cy.wait("@updateLayout"); + cy.assertPageSave(); + cy.wait(800); }); }, ); diff --git a/app/client/cypress/e2e/Regression/ClientSide/Widgets/TableV2/TableV2_Button_Icon_validation_spec.js b/app/client/cypress/e2e/Regression/ClientSide/Widgets/TableV2/TableV2_Button_Icon_validation_spec.js index 955087e218..83ba744fa2 100644 --- a/app/client/cypress/e2e/Regression/ClientSide/Widgets/TableV2/TableV2_Button_Icon_validation_spec.js +++ b/app/client/cypress/e2e/Regression/ClientSide/Widgets/TableV2/TableV2_Button_Icon_validation_spec.js @@ -23,9 +23,9 @@ describe( //cy.createModal("Modal", this.dataSet.ModalName); cy.createModal("Modal", "onRowSelected"); cy.isSelectRow(1); - cy.get(".bp3-overlay-backdrop").click({ force: true }); + cy.get(".bp3-overlay-backdrop").last().click({ force: true }); cy.isSelectRow(2); - cy.get(".bp3-overlay-backdrop").click({ force: true }); + cy.get(".bp3-overlay-backdrop").last().click({ force: true }); }); it("2. Table widget V2 with button colour change validation", function () { diff --git a/app/client/cypress/e2e/Regression/ServerSide/GenerateCRUD/Mongo_Spec.ts b/app/client/cypress/e2e/Regression/ServerSide/GenerateCRUD/Mongo_Spec.ts index 732d801b9c..dfa1c2c48f 100644 --- a/app/client/cypress/e2e/Regression/ServerSide/GenerateCRUD/Mongo_Spec.ts +++ b/app/client/cypress/e2e/Regression/ServerSide/GenerateCRUD/Mongo_Spec.ts @@ -13,7 +13,6 @@ import { table, } from "../../../../support/Objects/ObjectsCore"; import PageList from "../../../../support/Pages/PageList"; -import { PageLeftPane } from "../../../../support/Pages/EditorNavigation"; describe( "Validate Mongo CRUD with JSON Form", @@ -78,7 +77,7 @@ describe( deployMode.NavigateBacktoEditor(); table.WaitUntilTableLoad(1, 0, "v2"); //Delete the test data - PageLeftPane.expandCollapseItem("Pages"); + PageList.ShowList(); entityExplorer.ActionContextMenuByEntityName({ entityNameinLeftSidebar: "CoffeeCafe", action: "Delete", diff --git a/app/client/cypress/e2e/Regression/ServerSide/GenerateCRUD/MySQL1_Spec.ts b/app/client/cypress/e2e/Regression/ServerSide/GenerateCRUD/MySQL1_Spec.ts index c912e524d2..d0ee3d3d60 100644 --- a/app/client/cypress/e2e/Regression/ServerSide/GenerateCRUD/MySQL1_Spec.ts +++ b/app/client/cypress/e2e/Regression/ServerSide/GenerateCRUD/MySQL1_Spec.ts @@ -14,9 +14,7 @@ import EditorNavigation, { AppSidebar, AppSidebarButton, EntityType, - PageLeftPane, } from "../../../../support/Pages/EditorNavigation"; -import { featureFlagIntercept } from "../../../../support/Objects/FeatureFlags"; import PageList from "../../../../support/Pages/PageList"; let dsName: any; @@ -55,7 +53,7 @@ describe( deployMode.NavigateBacktoEditor(); table.WaitUntilTableLoad(0, 0, "v2"); //Delete the test data - PageLeftPane.expandCollapseItem("Pages"); + PageList.ShowList(); entityExplorer.ActionContextMenuByEntityName({ entityNameinLeftSidebar: "Page2", action: "Delete", @@ -123,7 +121,7 @@ describe( deployMode.NavigateBacktoEditor(); table.WaitUntilTableLoad(0, 0, "v2"); //Delete the test data - PageLeftPane.expandCollapseItem("Pages"); + PageList.ShowList(); entityExplorer.ActionContextMenuByEntityName({ entityNameinLeftSidebar: "Employees", action: "Delete", diff --git a/app/client/cypress/e2e/Regression/ServerSide/GenerateCRUD/Postgres1_Spec.ts b/app/client/cypress/e2e/Regression/ServerSide/GenerateCRUD/Postgres1_Spec.ts index 5f6b393ee5..70e6147c56 100644 --- a/app/client/cypress/e2e/Regression/ServerSide/GenerateCRUD/Postgres1_Spec.ts +++ b/app/client/cypress/e2e/Regression/ServerSide/GenerateCRUD/Postgres1_Spec.ts @@ -15,7 +15,6 @@ import EditorNavigation, { AppSidebar, AppSidebarButton, EntityType, - PageLeftPane, } from "../../../../support/Pages/EditorNavigation"; import PageList from "../../../../support/Pages/PageList"; @@ -50,7 +49,7 @@ describe( deployMode.NavigateBacktoEditor(); table.WaitUntilTableLoad(0, 0, "v2"); //Delete the test data - PageLeftPane.expandCollapseItem("Pages"); + PageList.ShowList(); entityExplorer.ActionContextMenuByEntityName({ entityNameinLeftSidebar: "Page2", action: "Delete", @@ -116,7 +115,7 @@ describe( deployMode.NavigateBacktoEditor(); table.WaitUntilTableLoad(0, 0, "v2"); //Delete the test data - PageLeftPane.expandCollapseItem("Pages"); + PageList.ShowList(); entityExplorer.ActionContextMenuByEntityName({ entityNameinLeftSidebar: "Public.orders", action: "Delete", diff --git a/app/client/cypress/e2e/Regression/ServerSide/GenerateCRUD/S3_Spec.js b/app/client/cypress/e2e/Regression/ServerSide/GenerateCRUD/S3_Spec.js index 9cf6db1030..7023f81a57 100644 --- a/app/client/cypress/e2e/Regression/ServerSide/GenerateCRUD/S3_Spec.js +++ b/app/client/cypress/e2e/Regression/ServerSide/GenerateCRUD/S3_Spec.js @@ -142,20 +142,10 @@ describe( // }); //Create Dummy Page2 : - cy.CreatePage(); - cy.wait("@createPage").should( - "have.nested.property", - "response.body.responseMeta.status", - 201, - ); + PageList.AddNewPage(); //Creating CRUD Page3 - cy.CreatePage(); - cy.wait("@createPage").should( - "have.nested.property", - "response.body.responseMeta.status", - 201, - ); + PageList.AddNewPage(); cy.get("@dSName").then((dbName) => { PageList.AddNewPage("Generate page with data"); @@ -227,7 +217,7 @@ describe( }); it("4. Generate CRUD page from the page menu", function () { - cy.GenerateCRUD(); + PageList.AddNewPage("Generate page with data"); cy.NavigateToDSGeneratePage(datasourceName); // fetch bucket cy.wait("@getDatasourceStructure").should( diff --git a/app/client/cypress/e2e/Regression/ServerSide/QueryPane/Mongo1_spec.ts b/app/client/cypress/e2e/Regression/ServerSide/QueryPane/Mongo1_spec.ts index 8813d0edd1..0fb427656f 100644 --- a/app/client/cypress/e2e/Regression/ServerSide/QueryPane/Mongo1_spec.ts +++ b/app/client/cypress/e2e/Regression/ServerSide/QueryPane/Mongo1_spec.ts @@ -14,7 +14,6 @@ import { } from "../../../../support/Objects/ObjectsCore"; import EditorNavigation, { EntityType, - PageLeftPane, } from "../../../../support/Pages/EditorNavigation"; import PageList from "../../../../support/Pages/PageList"; @@ -728,7 +727,7 @@ describe( deployMode.NavigateBacktoEditor(); table.WaitUntilTableLoad(0, 0, "v2"); //Delete the test data - PageLeftPane.expandCollapseItem("Pages"); + PageList.ShowList(); entityExplorer.ActionContextMenuByEntityName({ entityNameinLeftSidebar: "AuthorNAwards", action: "Delete", diff --git a/app/client/cypress/e2e/Sanity/Datasources/MsSQL_Basic_Spec.ts b/app/client/cypress/e2e/Sanity/Datasources/MsSQL_Basic_Spec.ts index 2d9b228450..18fba758aa 100644 --- a/app/client/cypress/e2e/Sanity/Datasources/MsSQL_Basic_Spec.ts +++ b/app/client/cypress/e2e/Sanity/Datasources/MsSQL_Basic_Spec.ts @@ -16,7 +16,6 @@ import oneClickBindingLocator from "../../../locators/OneClickBindingLocator"; import { OneClickBinding } from "../../Regression/ClientSide/OneClickBinding/spec_utility"; import EditorNavigation, { EntityType, - PageLeftPane, } from "../../../support/Pages/EditorNavigation"; import PageList from "../../../support/Pages/PageList"; @@ -308,7 +307,7 @@ describe( deployMode.NavigateBacktoEditor(); table.WaitUntilTableLoad(); //Delete the test data - PageLeftPane.expandCollapseItem("Pages"); + PageList.ShowList(); entityExplorer.ActionContextMenuByEntityName({ entityNameinLeftSidebar: "Page2", action: "Delete", diff --git a/app/client/cypress/locators/Pages.json b/app/client/cypress/locators/Pages.json index 7952319436..850fb3571f 100644 --- a/app/client/cypress/locators/Pages.json +++ b/app/client/cypress/locators/Pages.json @@ -3,7 +3,6 @@ "formWidgets": ".t--page-sidebar-FormWidgets", "viewWidgets": ".t--page-sidebar-ViewWidgets", "widgetsEditor": ".t--nav-link-widgets-editor", - "AddPage": ".pages .t--entity-add-btn", "Menuaction": ".bp3-overlay-open>.bp3-transition-container", "Delete": ":nth-child(2) > .bp3-menu-item", "apiEditorIcon": ".t--nav-link-api-editor", diff --git a/app/client/cypress/locators/commonlocators.json b/app/client/cypress/locators/commonlocators.json index 7443ea1aaf..cd6f50d6e6 100644 --- a/app/client/cypress/locators/commonlocators.json +++ b/app/client/cypress/locators/commonlocators.json @@ -81,7 +81,6 @@ "evaluatedCurrentValue": "div:last-of-type .t--CodeEditor-evaluatedValue > div:last-of-type pre", "entityExplorersearch": "#entity-explorer-search", "saveStatusContainer": ".t--save-status-container", - "saveStatusIsSaving": "t--save-status-is-saving", "statusSaving": ".t--save-status-is-saving", "saveStatusError": ".t--save-status-error", "selectWidgetVirtualList": ".menu-virtual-list div", diff --git a/app/client/cypress/locators/explorerlocators.json b/app/client/cypress/locators/explorerlocators.json index 8911f6abcc..282d66ad33 100644 --- a/app/client/cypress/locators/explorerlocators.json +++ b/app/client/cypress/locators/explorerlocators.json @@ -2,7 +2,6 @@ "NoApiMsg": "p:contains('No APIs yet.')", "NoQueryMsg": "p:contains('No DB Queries yet.')", "NoWidgetsMsg": "p:contains('icon above to add widgets')", - "AddPage": ".pages .t--entity-add-btn", "createQueryMenu": ".file-ops", "entityExplorer": ".t--entity-explorer", "popover": "//div[contains(@class,'t--entity page')]//*[local-name()='g' and @id='Icon/Outline/more-vertical']", diff --git a/app/client/cypress/support/Pages/EditorNavigation.ts b/app/client/cypress/support/Pages/EditorNavigation.ts index 273d9d3bf0..b016731c4c 100644 --- a/app/client/cypress/support/Pages/EditorNavigation.ts +++ b/app/client/cypress/support/Pages/EditorNavigation.ts @@ -3,6 +3,7 @@ import { ObjectsRegistry as _ } from "../Objects/Registry"; import ClickOptions = Cypress.ClickOptions; import { Sidebar } from "./IDE/Sidebar"; import { LeftPane } from "./IDE/LeftPane"; +import PageList from "./PageList"; export enum AppSidebarButton { Data = "Data", @@ -79,7 +80,7 @@ class EditorNavigation { NavigateToPage(name: string, networkCallAlias = false) { AppSidebar.navigate(AppSidebarButton.Editor); - PageLeftPane.expandCollapseItem("Pages"); + PageList.ShowList(); PageLeftPane.selectItem(name, { multiple: true, force: true }); _.AggregateHelper.Sleep(); //for selection to settle networkCallAlias && _.AssertHelper.AssertNetworkStatus("pageSnap"); diff --git a/app/client/cypress/support/Pages/EntityExplorer.ts b/app/client/cypress/support/Pages/EntityExplorer.ts index 34775b923b..b96c9dd114 100644 --- a/app/client/cypress/support/Pages/EntityExplorer.ts +++ b/app/client/cypress/support/Pages/EntityExplorer.ts @@ -7,6 +7,7 @@ import EditorNavigation, { PageLeftPane, PagePaneSegment, } from "./EditorNavigation"; +import PageList from "./PageList"; type templateActions = | "Find" @@ -255,6 +256,7 @@ export class EntityExplorer { viaMenu = false, ) { AppSidebar.navigate(AppSidebarButton.Editor); + PageList.ShowList(); if (viaMenu) this.ActionContextMenuByEntityName({ entityNameinLeftSidebar: entityName, diff --git a/app/client/cypress/support/Pages/PageList.ts b/app/client/cypress/support/Pages/PageList.ts index 5bfc87f47e..ca89ff269f 100644 --- a/app/client/cypress/support/Pages/PageList.ts +++ b/app/client/cypress/support/Pages/PageList.ts @@ -11,6 +11,7 @@ class PageList { `.t--entity.page:contains('${pageName}')`, newButton: ".pages .t--entity-add-btn", newPageOption: (option: string) => `//span[text()='${option}']/parent::div`, + switcher: `.t--pages-switcher`, }; public AddNewPage( @@ -20,12 +21,14 @@ class PageList { | "Add page from template" = "New blank page", ) { AppSidebar.navigate(AppSidebarButton.Editor); + this.ShowList(); ObjectsRegistry.AggregateHelper.GetNClick(this.locators.newButton); ObjectsRegistry.AggregateHelper.GetNClick( this.locators.newPageOption(option), ); if (option === "New blank page") { ObjectsRegistry.AssertHelper.AssertNetworkStatus("@createPage", 201); + return cy .get("@createPage") .then(($pageName: any) => $pageName.response?.body.data.name); @@ -33,6 +36,7 @@ class PageList { } public VerifyIsCurrentPage(pageName: string) { + this.ShowList(); ObjectsRegistry.AggregateHelper.GetElement( this.locators.pageListItem(pageName), ).should("have.class", "activePage"); @@ -44,6 +48,7 @@ class PageList { public ClonePage(pageName = "Page1") { AppSidebar.navigate(AppSidebarButton.Editor); + this.ShowList(); EditorNavigation.SelectEntityByName(pageName, EntityType.Page); ObjectsRegistry.EntityExplorer.ActionContextMenuByEntityName({ entityNameinLeftSidebar: pageName, @@ -52,17 +57,41 @@ class PageList { ObjectsRegistry.AssertHelper.AssertNetworkStatus("@clonePage", 201); } + public ShowList() { + cy.get(this.locators.switcher).then(($switcher) => { + const isActive: string | undefined = $switcher.attr("data-active"); + if (isActive === "false") { + cy.get(this.locators.switcher).click(); + } + }); + } + assertPresence(pageName: string) { + this.ShowList(); ObjectsRegistry.AggregateHelper.AssertElementVisibility( this.locators.pageListItem(pageName), ); } assertAbsence(pageName: string) { + this.ShowList(); ObjectsRegistry.AggregateHelper.AssertElementAbsence( this.locators.pageListItem(pageName), ); } + + DeletePage(name: string) { + this.ShowList(); + cy.get(this.locators.pageListItem(name)).within(() => { + cy.get(".t--context-menu").click({ force: true }); + }); + cy.wait(2000); + cy.selectAction("Delete"); + cy.selectAction("Are you sure?"); + cy.wait("@deletePage") + .its("response.body.responseMeta.status") + .should("eq", 200); + } } export default new PageList(); diff --git a/app/client/cypress/support/commands.js b/app/client/cypress/support/commands.js index 0cbfb2d98b..5e3297359b 100644 --- a/app/client/cypress/support/commands.js +++ b/app/client/cypress/support/commands.js @@ -5,7 +5,6 @@ import { ANVIL_EDITOR_TEST } from "./Constants.js"; import EditorNavigation, { EntityType, - AppSidebarButton, AppSidebar, PageLeftPane, PagePaneSegment, @@ -24,7 +23,6 @@ const loginPage = require("../locators/LoginPage.json"); const signupPage = require("../locators/SignupPage.json"); import homePage from "../locators/HomePage"; -const pages = require("../locators/Pages.json"); const commonlocators = require("../locators/commonlocators.json"); const widgetsPage = require("../locators/Widgets.json"); import ApiEditor from "../locators/ApiEditor"; @@ -390,14 +388,6 @@ Cypress.Commands.add("DeleteApp", (appName) => { cy.get(homePage.deleteApp).contains("Are you sure?").click({ force: true }); }); -Cypress.Commands.add("DeletepageFromSideBar", () => { - cy.xpath(pages.popover).last().click({ force: true }); - cy.get(pages.deletePage).first().click({ force: true }); - cy.get(pages.deletePageConfirm).first().click({ force: true }); - // eslint-disable-next-line cypress/no-unnecessary-waiting - cy.wait(2000); -}); - Cypress.Commands.add("LogOut", (toCheckgetPluginForm = true) => { agHelper.WaitUntilAllToastsDisappear(); //Since these are coming in every self-hosted 1st time login, commenting for CI runs @@ -1952,22 +1942,6 @@ Cypress.Commands.add( }, ); -Cypress.Commands.add("CreatePage", () => { - AppSidebar.navigate(AppSidebarButton.Editor); - cy.get(pages.AddPage).first().click(); - cy.xpath("//span[text()='New blank page']/parent::div").click(); -}); - -Cypress.Commands.add("GenerateCRUD", () => { - cy.get(pages.AddPage).first().click(); - cy.xpath("//span[text()='Generate page with data']/parent::div").click(); -}); - -Cypress.Commands.add("AddPageFromTemplate", () => { - cy.get(pages.AddPage).first().click(); - cy.xpath("//span[text()='Add page from template']/parent::div").click(); -}); - Cypress.Commands.add(`verifyCallCount`, (alias, expectedNumberOfCalls) => { cy.wait(alias); cy.get(`${alias}.all`).should("have.length", expectedNumberOfCalls); diff --git a/app/client/cypress/support/index.d.ts b/app/client/cypress/support/index.d.ts new file mode 100644 index 0000000000..2126de3a5b --- /dev/null +++ b/app/client/cypress/support/index.d.ts @@ -0,0 +1,179 @@ +/// + +declare namespace Cypress { + interface Chainable { + SignupFromAPI(uname: string, password: string); + dragTo(subject: any, targetEl: any); + downloadData(filetype: string); + validateDownload(fileName: string); + AddFilterWithOperator( + operator: string, + option: string, + condition: string, + value: string, + ); + stubPostHeaderReq(); + addOAuth2ClientCredentialsDetails( + accessTokenUrl: string, + clientId: string, + clientSecret: string, + scope: string, + ); + addOAuth2AuthorizationCodeDetails( + accessTokenUrl: string, + clientId: string, + clientSecret: string, + authURL: string, + ); + testSelfSignedCertificateSettingsInREST(isOAuth2: boolean); + addBasicProfileDetails(username: string, password: string); + DeleteApp(appName: string); + GetUrlQueryParams(); + LogOutUser(); + LoginUser(uname: string, pword: string, goToLoginPage?: boolean); + LogintoApp(uname: string, pword: string); + LogintoAppTestUser(uname: string, pword: string); + Signup(uname: string, pword: string); + LoginFromAPI(uname: string, pword: string); + DeletepageFromSideBar(); + LogOut(toCheckgetPluginForm?: boolean); + SearchApp(appname: string); + WaitAutoSave(); + SelectAction(action: string); + ClearSearch(); + paste($element: any, text: string); + clickTest(testbutton: string); + EvaluateCurrentValue( + currentValue: string, + isValueToBeEvaluatedDynamic?: boolean, + ); + tabPopertyUpdate(tabId: string, newTabName: string); + generateUUID(); + addDsl(dsl: any); + DeleteAppByApi(); + DeleteWorkspaceByApi(); + togglebar(value: string); + radiovalue(value: string, value2: string); + optionValue(value: string, value2: string); + typeIntoDraftEditor(selector: string, text: string); + getPluginFormsAndCreateDatasource(); + NavigateToJSEditor(); + importCurl(); + selectAction(option: string); + deleteActionAndConfirm(); + deleteJSObject(); + deleteDataSource(); + dragAndDropToCanvas(widgetType: string, { x: number, y: number }); + dragAndDropToWidget( + widgetType: string, + destinationWidget: string, + { x: number, y: number }, + ); + dragAndDropToWidgetBySelector( + widgetType: string, + destinationSelector: string, + { x: number, y: number }, + ); + changeButtonColor(buttonColor: string); + closePropertyPane(); + onClickActions( + forSuccess: string, + forFailure: string, + actionType: string, + actionValue: string, + idx?: number, + ); + isSelectRow(index: number); + getDate(date: number, dateFormate: string); + setDate(date: number, dateFormate: string); + pageNo(); + pageNoValidate(index: number); + validateDisableWidget(widgetCss: string, disableCss: string); + validateToolbarVisible(widgetCss: string, toolbarCss: string); + validateToolbarHidden(widgetCss: string, toolbarCss: string); + validateEnableWidget(widgetCss: string, disableCss: string); + validateHTMLText(widgetCss: string, htmlTag: string, value: string); + setTinyMceContent(tinyMceId: string, content: string); + startRoutesForDatasource(); + startServerAndRoutes(); + startErrorRoutes(); + NavigateToPaginationTab(); + ValidateTableData(value: string); + ValidateTableV2Data(value: string); + ValidatePublishTableData(value: string); + ValidatePublishTableV2Data(value: string); + ValidatePaginateResponseUrlData(runTestCss: string); + ValidatePaginateResponseUrlDataV2(runTestCss: string); + ValidatePaginationInputData(valueToTest: string); + ValidatePaginationInputDataV2(valueToTest: string); + CheckForPageSaveError(); + assertPageSave(validateSavedState?: boolean); + validateCodeEditorContent(selector: string, contentToValidate: string); + updateMapType(mapType: string); + createJSObject(JSCode: string); + createSuperUser(); + SignupFromAPI(uname: string, pword: string); + startInterceptRoutesForMySQL(); + startInterceptRoutesForMongo(); + startInterceptRoutesForS3(); + replaceApplicationIdForInterceptPages(fixtureFile: string); + paste(selector: string, pastePayload: string); + typeValueNValidate( + valueToType: string, + fieldName?: string, + isDynamic?: boolean, + ); + checkCodeInputValue(selector: string); + clickButton(btnVisibleText: string, toForceClick?: boolean); + actionContextMenuByEntityName( + entityNameinLeftSidebar: string, + action?: string, + subActions: string, + ); + selectEntityByName(entityNameinLeftSidebar: string); + EvaluatFieldValue(fieldName?: string, currentValue?: string); + renameWithInPane(renameVal: string); + getEntityName(); + VerifyErrorMsgAbsence(errorMsgToVerifyAbsence: string); + VerifyErrorMsgPresence(errorMsgToVerifyAbsence: string); + setQueryTimeout(timeout: string); + VerifyNoDataDisplayAbsence(); + isNotInViewport(element: string); + isInViewport(element: string); + CheckAndUnfoldEntityItem(item: string); + DeleteEntityStateLocalStorage(); + checkLabelForWidget(options: string); + saveLocalStorageCache(); + restoreLocalStorageCache(); + StopContainer(path: string, containerName: string); + StopAllContainer(path: string); + StartContainer(path: string, containerName: string); + StartNewContainer( + url: string, + path: string, + version: string, + containerName: string, + ); + GetPath(path: string, containerName: string); + GetCWD(path: string); + GetAndVerifyLogs(path: string, containerName: string); + typeTab(); + CreatePage(); + GenerateCRUD(); + AddPageFromTemplate(); + verifyCallCount(alias: string, expectedNumberOfCalls: number); + RenameWidgetFromPropertyPane( + widgetType: string, + oldName: string, + newName: string, + ); + forceVisit(url: string); + SelectDropDown(dropdownOption: string); + RemoveMultiSelectItems(dropdownOptions: string[]); + RemoveAllSelections(); + SelectFromMultiSelect(options: string); + skipSignposting(); + stubPricingPage(); + validateEvaluatedValue(value: string); + } +} diff --git a/app/client/cypress/support/widgetCommands.js b/app/client/cypress/support/widgetCommands.js index 48e5da8f26..113b931233 100644 --- a/app/client/cypress/support/widgetCommands.js +++ b/app/client/cypress/support/widgetCommands.js @@ -1,6 +1,8 @@ /* eslint-disable cypress/no-unnecessary-waiting */ /* eslint-disable cypress/no-assigning-return-values */ +import PageList from "./Pages/PageList"; + require("cy-verify-downloads").addCustomCommand(); require("cypress-file-upload"); const commonlocators = require("../locators/commonlocators.json"); @@ -929,31 +931,17 @@ Cypress.Commands.add("DeleteModal", () => { }); Cypress.Commands.add("Createpage", (pageName, navigateToCanvasPage = true) => { - cy.CreatePage(); - cy.wait("@createPage").then((xhr) => { - expect(xhr.response.body.responseMeta.status).to.equal(201); + PageList.AddNewPage().then((oldPageName) => { if (pageName) { - const pageId = xhr.response.body.data.id; - const oldPageName = xhr.response.body.data.name; cy.wait(2000); ee.RenameEntityFromExplorer(oldPageName, pageName, true); - cy.wrap(pageId).as("currentPageId"); } cy.get("#loading").should("not.exist"); }); -}); - -Cypress.Commands.add("Deletepage", (Pagename) => { - cy.CheckAndUnfoldEntityItem("Pages"); - cy.get(`.t--entity-item:contains(${Pagename})`).within(() => { - cy.get(".t--context-menu").click({ force: true }); + cy.get("@createPage").then((xhr) => { + const pageId = xhr.response.body.data.id; + cy.wrap(pageId).as("currentPageId"); }); - cy.wait(2000); - cy.selectAction("Delete"); - cy.selectAction("Are you sure?"); - cy.wait("@deletePage") - .its("response.body.responseMeta.status") - .should("eq", 200); }); Cypress.Commands.add("dropdownDynamic", (text) => { diff --git a/app/client/package.json b/app/client/package.json index 4f9717681d..b9ff538613 100644 --- a/app/client/package.json +++ b/app/client/package.json @@ -110,8 +110,8 @@ "d3-geo": "^3.1.0", "dayjs": "^1.10.6", "deep-diff": "^1.0.2", - "design-system": "npm:@appsmithorg/design-system@2.1.35", - "design-system-old": "npm:@appsmithorg/design-system-old@1.1.15", + "design-system": "npm:@appsmithorg/design-system@2.1.36", + "design-system-old": "npm:@appsmithorg/design-system-old@1.1.16", "downloadjs": "^1.4.7", "echarts": "^5.4.2", "fast-deep-equal": "^3.1.3", diff --git a/app/client/src/actions/pluginActionActions.ts b/app/client/src/actions/pluginActionActions.ts index 65323ce66f..291dcc982d 100644 --- a/app/client/src/actions/pluginActionActions.ts +++ b/app/client/src/actions/pluginActionActions.ts @@ -3,7 +3,6 @@ import type { EvaluationReduxAction, AnyReduxAction, ReduxAction, - ReduxActionWithoutPayload, } from "@appsmith/constants/ReduxActionConstants"; import type { JSUpdate } from "utils/JSPaneUtils"; import { @@ -11,6 +10,7 @@ import { ReduxActionTypes, } from "@appsmith/constants/ReduxActionConstants"; import type { Action, ActionViewMode } from "entities/Action"; +import { ActionExecutionContext } from "entities/Action"; import { batchAction } from "actions/batchActions"; import type { ExecuteErrorPayload } from "constants/AppsmithActionConstants/ActionConstants"; import type { ModalInfo } from "reducers/uiReducers/modalActionReducer"; @@ -107,6 +107,8 @@ export const runAction = ( id: string, paginationField?: PaginationField, skipOpeningDebugger = false, + action = undefined, + actionExecutionContext = ActionExecutionContext.SELF, ) => { return { type: ReduxActionTypes.RUN_ACTION_REQUEST, @@ -114,6 +116,8 @@ export const runAction = ( id, paginationField, skipOpeningDebugger, + action, + actionExecutionContext, }, }; }; @@ -314,9 +318,16 @@ export const updateActionProperty = ( }); }; -export const executePageLoadActions = (): ReduxActionWithoutPayload => ({ - type: ReduxActionTypes.EXECUTE_PAGE_LOAD_ACTIONS, -}); +export const executePageLoadActions = ( + actionExecutionContext?: ActionExecutionContext, +) => { + return { + type: ReduxActionTypes.EXECUTE_PAGE_LOAD_ACTIONS, + payload: { + actionExecutionContext, + }, + }; +}; export const executeJSUpdates = ( payload: Record, diff --git a/app/client/src/actions/widgetActions.tsx b/app/client/src/actions/widgetActions.tsx index b67ca7ef21..0d16591262 100644 --- a/app/client/src/actions/widgetActions.tsx +++ b/app/client/src/actions/widgetActions.tsx @@ -47,9 +47,15 @@ export const createModalAction = ( export const focusWidget = ( widgetId?: string, -): ReduxAction<{ widgetId?: string }> => ({ + alt?: boolean, +): ReduxAction<{ widgetId?: string; alt?: boolean }> => ({ type: ReduxActionTypes.FOCUS_WIDGET, - payload: { widgetId }, + payload: { widgetId, alt }, +}); + +export const altFocusWidget = (alt: boolean) => ({ + type: ReduxActionTypes.ALT_FOCUS_WIDGET, + payload: alt, }); export const showModal = (id: string, shouldSelectModal = true) => { @@ -144,3 +150,10 @@ export const partialExportWidgets = (params: PartialExportParams) => { payload: params, }; }; + +export const setWidgetSelectionBlock = (payload: boolean) => { + return { + type: ReduxActionTypes.SET_WIDGET_SELECTION_BLOCK, + payload, + }; +}; diff --git a/app/client/src/api/AppThemingApi.tsx b/app/client/src/api/AppThemingApi.tsx index 39969d6135..695c5b2583 100644 --- a/app/client/src/api/AppThemingApi.tsx +++ b/app/client/src/api/AppThemingApi.tsx @@ -68,23 +68,6 @@ class AppThemingApi extends API { ); } - /** - * fires api for saving current theme - * - * @param applicationId - * @param theme - * @returns - */ - static async saveTheme( - applicationId: string, - payload: { name: string }, - ): Promise>> { - return API.patch( - `${AppThemingApi.baseUrl}/themes/applications/${applicationId}`, - payload, - ); - } - /** * fires api for deleting theme * diff --git a/app/client/src/ce/actions/workspaceActions.ts b/app/client/src/ce/actions/workspaceActions.ts index a3b3cc1db5..b061770c6a 100644 --- a/app/client/src/ce/actions/workspaceActions.ts +++ b/app/client/src/ce/actions/workspaceActions.ts @@ -129,3 +129,7 @@ export const fetchEntitiesOfWorkspace = (payload: { workspaceId?: string }) => { payload, }; }; + +export const resetImportData = () => ({ + type: ReduxActionTypes.RESET_IMPORT_DATA, +}); diff --git a/app/client/src/ce/constants/ModuleConstants.ts b/app/client/src/ce/constants/ModuleConstants.ts index 7cb873c206..856db60531 100644 --- a/app/client/src/ce/constants/ModuleConstants.ts +++ b/app/client/src/ce/constants/ModuleConstants.ts @@ -1,3 +1,5 @@ +import type { PluginType } from "entities/Action"; + type ID = string; export enum MODULE_TYPE { @@ -15,9 +17,17 @@ export interface ModuleInputSection { children?: ModuleInput[]; } -export interface Module { +export interface Module extends ModuleMetadata { id: ID; name: string; packageId: ID; inputsForm: ModuleInputSection[]; + type: MODULE_TYPE; +} + +export interface ModuleMetadata { + moduleId: string; + datasourceId?: string; + pluginId: string; + pluginType: PluginType; } diff --git a/app/client/src/ce/constants/ModuleInstanceConstants.ts b/app/client/src/ce/constants/ModuleInstanceConstants.ts index 526b042b92..b5721d8497 100644 --- a/app/client/src/ce/constants/ModuleInstanceConstants.ts +++ b/app/client/src/ce/constants/ModuleInstanceConstants.ts @@ -15,6 +15,7 @@ export interface ModuleInstance { inputs: { [key: string]: string; }; + sourceModuleId: ModuleId; } export interface ModuleInstanceData { diff --git a/app/client/src/ce/constants/ReduxActionConstants.tsx b/app/client/src/ce/constants/ReduxActionConstants.tsx index 0521c7a384..de8c869fad 100644 --- a/app/client/src/ce/constants/ReduxActionConstants.tsx +++ b/app/client/src/ce/constants/ReduxActionConstants.tsx @@ -546,6 +546,7 @@ const ActionTypes = { IMPORT_APPLICATION_FROM_GIT_INIT: "IMPORT_APPLICATION_FROM_GIT_INIT", IMPORT_APPLICATION_SUCCESS: "IMPORT_APPLICATION_SUCCESS", SET_WIDGET_LOADING: "SET_WIDGET_LOADING", + RESET_IMPORT_DATA: "RESET_IMPORT_DATA", SET_GLOBAL_SEARCH_QUERY: "SET_GLOBAL_SEARCH_QUERY", SET_GLOBAL_SEARCH_CATEGORY: "SET_GLOBAL_SEARCH_CATEGORY", TOGGLE_SHOW_GLOBAL_SEARCH_MODAL: "TOGGLE_SHOW_GLOBAL_SEARCH_MODAL", @@ -687,7 +688,6 @@ const ActionTypes = { CHANGE_SELECTED_APP_THEME_SUCCESS: "CHANGE_SELECTED_APP_THEME_SUCCESS", SET_PREVIEW_APP_THEME: "SET_PREVIEW_APP_THEME", SAVE_APP_THEME_INIT: "SAVE_APP_THEME_INIT", - SAVE_APP_THEME_SUCCESS: "SAVE_APP_THEME_SUCCESS", DELETE_APP_THEME_INIT: "DELETE_APP_THEME_INIT", DELETE_APP_THEME_SUCCESS: "DELETE_APP_THEME_SUCCESS", RESET_APP_THEME_INIT: "RESET_APP_THEME_INIT", @@ -917,6 +917,8 @@ const ActionTypes = { SET_API_PANE_DEBUGGER_STATE: "SET_API_PANE_DEBUGGER_STATE", SET_JS_PANE_DEBUGGER_STATE: "SET_JS_PANE_DEBUGGER_STATE", SET_CANVAS_DEBUGGER_STATE: "SET_CANVAS_DEBUGGER_STATE", + SET_WIDGET_SELECTION_BLOCK: "SET_WIDGET_SELECTION_BLOCK", + ALT_FOCUS_WIDGET: "ALT_FOCUS_WIDGET", }; export const ReduxActionTypes = { @@ -1078,7 +1080,6 @@ export const ReduxActionErrorTypes = { UPDATE_JS_FUNCTION_PROPERTY_ERROR: "UPDATE_JS_FUNCTION_PROPERTY_ERROR", DELETE_WORKSPACE_ERROR: "DELETE_WORKSPACE_ERROR", REFLOW_BETA_FLAGS_INIT_ERROR: "REFLOW_BETA_FLAGS_INIT_ERROR", - SAVE_APP_THEME_ERROR: "SAVE_APP_THEME_ERROR", DELETE_APP_THEME_ERROR: "DELETE_APP_THEME_ERROR", GET_ALL_TEMPLATES_ERROR: "GET_ALL_TEMPLATES_ERROR", GET_SIMILAR_TEMPLATES_ERROR: "GET_SIMILAR_TEMPLATES_ERROR", diff --git a/app/client/src/ce/constants/messages.ts b/app/client/src/ce/constants/messages.ts index 9bb3e1a5b4..9a8ea0143d 100644 --- a/app/client/src/ce/constants/messages.ts +++ b/app/client/src/ce/constants/messages.ts @@ -2459,3 +2459,8 @@ export const CREATE_A_NEW_ITEM = (item: string) => `Create a new ${item}`; export const MAXIMIZE_BUTTON_TOOLTIP = () => `Expand code editor to full-screen`; export const MINIMIZE_BUTTON_TOOLTIP = () => `Open code editor next to the UI`; +export const SPLITPANE_ANNOUNCEMENT = { + TITLE: () => "Code and UI, side-by-side", + DESCRIPTION: () => + "Write queries and JS functions while you refer to the UI on the side! This is a beta version that we will continue to improve with your feedback.", +}; diff --git a/app/client/src/ce/pages/Applications/ResourceListLoader.tsx b/app/client/src/ce/pages/Applications/ResourceListLoader.tsx index 3007567db2..9d364b4ab8 100644 --- a/app/client/src/ce/pages/Applications/ResourceListLoader.tsx +++ b/app/client/src/ce/pages/Applications/ResourceListLoader.tsx @@ -14,7 +14,7 @@ interface ResourcesLoaderProps { const DEFAULT_BACKGROUND_COLOR = "#9747FF1A"; const DEFAULT_ICON = "book"; -const DEAFULT_RESOURCES = [{ name: "Default Resource" }]; +const DEAFULT_RESOURCES = [{ id: "default", name: "Default Resource" }]; function ResourceListLoader({ isMobile, resources }: ResourcesLoaderProps) { const resourcesToUse = resources?.length ? resources : DEAFULT_RESOURCES; diff --git a/app/client/src/ce/pages/Applications/index.tsx b/app/client/src/ce/pages/Applications/index.tsx index 14b6733899..9bf7751955 100644 --- a/app/client/src/ce/pages/Applications/index.tsx +++ b/app/client/src/ce/pages/Applications/index.tsx @@ -12,7 +12,6 @@ import { createMessage, INVITE_USERS_PLACEHOLDER, NO_APPS_FOUND, - NO_WORKSPACE_DESCRIPTION, NO_WORKSPACE_HEADING, WORKSPACES_HEADING, } from "@appsmith/constants/messages"; @@ -370,7 +369,6 @@ export function WorkspaceMenuItem({ isFetchingWorkspaces ? 100 : 22 } /* this is to avoid showing tooltip for loaders */ icon="group-2-line" - key={workspace?.id} onSelect={handleWorkspaceClick} selected={selected} text={workspace?.name} @@ -387,8 +385,8 @@ export const submitCreateWorkspaceForm = async (data: any, dispatch: any) => { export interface LeftPaneProps { isBannerVisible?: boolean; isFetchingWorkspaces: boolean; - workspaces: any; - activeWorkspaceId: string | undefined; + workspaces: Workspace[]; + activeWorkspaceId?: string; } export function LeftPane(props: LeftPaneProps) { @@ -396,7 +394,7 @@ export function LeftPane(props: LeftPaneProps) { activeWorkspaceId, isBannerVisible = false, isFetchingWorkspaces, - workspaces, + workspaces = [], } = props; const isMobile = useIsMobileDevice(); @@ -409,18 +407,14 @@ export function LeftPane(props: LeftPaneProps) { isFetchingWorkspaces={isFetchingWorkspaces} > - {workspaces && - workspaces.map( - (workspace: any) => - workspace && ( - - ), - )} + {workspaces.map((workspace) => ( + + ))} @@ -565,11 +559,14 @@ export function ApplicationsSection(props: any) { setSelectedWorkspaceIdForImportApplication, ]); - const leaveWS = (workspaceId: string) => { - setWarnLeavingWorkspace(false); - setWorkspaceToOpenMenu(null); - dispatch(leaveWorkspace(workspaceId)); - }; + const leaveWS = useCallback( + (workspaceId: string) => { + setWarnLeavingWorkspace(false); + setWorkspaceToOpenMenu(null); + dispatch(leaveWorkspace(workspaceId)); + }, + [dispatch], + ); const handleDeleteWorkspace = useCallback( (workspaceId: string) => { @@ -657,9 +654,6 @@ export function ApplicationsSection(props: any) { {createMessage(NO_WORKSPACE_HEADING)} - - {createMessage(NO_WORKSPACE_DESCRIPTION)} - ); } @@ -896,7 +890,9 @@ export const ApplictionsMainPage = (props: any) => { if (!isFetchingWorkspaces) { workspaces = fetchedWorkspaces; } else { - workspaces = loadingUserWorkspaces as any; + workspaces = loadingUserWorkspaces.map( + (loadingWorkspaces) => loadingWorkspaces.workspace, + ) as any; } const [activeWorkspaceId, setActiveWorkspaceId] = useState< diff --git a/app/client/src/ce/pages/Editor/IDE/EditorPane/Query/hooks.ts b/app/client/src/ce/pages/Editor/IDE/EditorPane/Query/hooks.ts index 40e8f50f4f..f9ee3a481b 100644 --- a/app/client/src/ce/pages/Editor/IDE/EditorPane/Query/hooks.ts +++ b/app/client/src/ce/pages/Editor/IDE/EditorPane/Query/hooks.ts @@ -60,7 +60,6 @@ export const useQueryAdd = () => { return addButtonClickHandler; }; -//history.push(location.pathname.replace(`${ADD_PATH}`, "")); export type GroupedAddOperations = Array<{ title?: string; @@ -214,7 +213,7 @@ export const useAddQueryListItems = () => { fileOperation.entityExplorerTitle || fileOperation.dsName || fileOperation.title, - description: "", + description: !!fileOperation.isBeta ? "Beta" : "", descriptionType: "inline", onClick: onCreateItemClick.bind(null, fileOperation), } as ListItemProps; diff --git a/app/client/src/ce/pages/Editor/gitSync/useReconnectModalData.ts b/app/client/src/ce/pages/Editor/gitSync/useReconnectModalData.ts new file mode 100644 index 0000000000..9109ef39af --- /dev/null +++ b/app/client/src/ce/pages/Editor/gitSync/useReconnectModalData.ts @@ -0,0 +1,33 @@ +import { builderURL } from "@appsmith/RouteBuilder"; +import { + RECONNECT_MISSING_DATASOURCE_CREDENTIALS_DESCRIPTION, + SKIP_TO_APPLICATION, + createMessage, +} from "@appsmith/constants/messages"; +import { EditorNames } from "@appsmith/hooks"; + +interface UseReconnectModalDataProps { + pageId: string | null; + appId: string | null; +} + +function useReconnectModalData({ appId, pageId }: UseReconnectModalDataProps) { + const editorURL = + pageId && + builderURL({ + pageId, + }); + + return { + skipMessage: createMessage(SKIP_TO_APPLICATION), + missingDsCredentialsDescription: createMessage( + RECONNECT_MISSING_DATASOURCE_CREDENTIALS_DESCRIPTION, + ), + editorURL, + editorId: appId, + parentEntityId: pageId, + editorType: EditorNames.APPLICATION, + }; +} + +export default useReconnectModalData; diff --git a/app/client/src/ce/pages/common/AppHeader.tsx b/app/client/src/ce/pages/common/AppHeader.tsx index 2821539d6e..7406aeeae5 100644 --- a/app/client/src/ce/pages/common/AppHeader.tsx +++ b/app/client/src/ce/pages/common/AppHeader.tsx @@ -18,22 +18,13 @@ import { } from "constants/routes"; import Navigation from "pages/AppViewer/Navigation"; import type { RouteComponentProps } from "react-router"; -import AppEditorHeader from "pages/Editor/EditorHeader"; -import { Header } from "pages/Editor/IDE/Header"; -import { useFeatureFlag } from "utils/hooks/useFeatureFlag"; -import { FEATURE_FLAG } from "@appsmith/entities/FeatureFlag"; +import { Header as AppIDEHeader } from "pages/Editor/IDE/Header"; export type Props = RouteComponentProps; export const headerRoot = document.getElementById("header-root"); export const Routes = () => { - const isSideBySideFlagEnabled = useFeatureFlag( - FEATURE_FLAG.release_side_by_side_ide_enabled, - ); - - const HeaderComponent = isSideBySideFlagEnabled ? Header : AppEditorHeader; - return ( @@ -46,10 +37,10 @@ export const Routes = () => { exact path={CUSTOM_WIDGETS_EDITOR_ID_PATH_CUSTOM} /> - + - - + + diff --git a/app/client/src/ce/reducers/uiReducers/applicationsReducer.tsx b/app/client/src/ce/reducers/uiReducers/applicationsReducer.tsx index 73094e5741..f13ad3b2f0 100644 --- a/app/client/src/ce/reducers/uiReducers/applicationsReducer.tsx +++ b/app/client/src/ce/reducers/uiReducers/applicationsReducer.tsx @@ -247,6 +247,12 @@ export const handlers = { importingApplication: false, }; }, + [ReduxActionTypes.RESET_IMPORT_DATA]: (state: ApplicationsReduxState) => { + return { + ...state, + importedApplication: null, + }; + }, [ReduxActionTypes.PARTIAL_IMPORT_INIT]: (state: ApplicationsReduxState) => ({ ...state, partialImportExport: { diff --git a/app/client/src/ce/sagas/NavigationSagas.ts b/app/client/src/ce/sagas/NavigationSagas.ts index 2bc4822fd7..a7547c2304 100644 --- a/app/client/src/ce/sagas/NavigationSagas.ts +++ b/app/client/src/ce/sagas/NavigationSagas.ts @@ -20,8 +20,10 @@ import { flushErrors } from "actions/errorActions"; import type { NavigationMethod } from "utils/history"; import UsagePulse from "usagePulse"; import { getIDETypeByUrl } from "@appsmith/entities/IDE/utils"; +import type { EditorViewMode } from "@appsmith/entities/IDE/constants"; import { IDE_TYPE } from "@appsmith/entities/IDE/constants"; import { updateIDETabsOnRouteChangeSaga } from "sagas/IDESaga"; +import { getIDEViewMode } from "selectors/ideSelectors"; let previousPath: string; @@ -110,6 +112,7 @@ function* logNavigationAnalytics(payload: RouteChangeActionPayload) { const isRecent = recentEntityIds.some( (entityId) => entityId === currentEntity.id, ); + const ideViewMode: EditorViewMode = yield select(getIDEViewMode); const { height, width } = window.screen; AnalyticsUtil.logEvent("ROUTE_CHANGE", { toPath: pathname, @@ -121,6 +124,7 @@ function* logNavigationAnalytics(payload: RouteChangeActionPayload) { fromType: previousEntity.entity, screenHeight: height, screenWidth: width, + editorMode: ideViewMode, }); } diff --git a/app/client/src/ce/sagas/PageSagas.tsx b/app/client/src/ce/sagas/PageSagas.tsx index 4eeed87b5f..d4b6fa320c 100644 --- a/app/client/src/ce/sagas/PageSagas.tsx +++ b/app/client/src/ce/sagas/PageSagas.tsx @@ -145,6 +145,7 @@ import type { DSLWidget } from "WidgetProvider/constants"; import type { FeatureFlags } from "@appsmith/entities/FeatureFlag"; import { getIsServerDSLMigrationsEnabled } from "selectors/pageSelectors"; import { getCurrentWorkspaceId } from "@appsmith/selectors/selectedWorkspaceSelectors"; +import { ActionExecutionContext } from "entities/Action"; export const checkIfMigrationIsNeeded = ( fetchPageResponse?: FetchPageResponse, @@ -977,7 +978,11 @@ export function* clonePageSaga( } yield put(selectWidgetInitAction(SelectionRequestType.Empty)); - yield put(fetchAllPageEntityCompletion([executePageLoadActions()])); + yield put( + fetchAllPageEntityCompletion([ + executePageLoadActions(ActionExecutionContext.CLONE_PAGE), + ]), + ); // TODO: Update URL params here. @@ -1374,7 +1379,11 @@ export function* generateTemplatePageSaga( if (!afterActionsFetch) { throw new Error("Failed generating template"); } - yield put(fetchAllPageEntityCompletion([executePageLoadActions()])); + yield put( + fetchAllPageEntityCompletion([ + executePageLoadActions(ActionExecutionContext.GENERATE_CRUD_PAGE), + ]), + ); history.replace( builderURL({ diff --git a/app/client/src/ce/sagas/userSagas.tsx b/app/client/src/ce/sagas/userSagas.tsx index dc84d0f5b2..4439ea2df9 100644 --- a/app/client/src/ce/sagas/userSagas.tsx +++ b/app/client/src/ce/sagas/userSagas.tsx @@ -602,6 +602,7 @@ export function* leaveWorkspaceSaga( toast.show(`You have successfully left the workspace`, { kind: "success", }); + history.push("/applications"); } } catch (error) { // do nothing as it's already handled globally diff --git a/app/client/src/ce/selectors/modulesSelector.ts b/app/client/src/ce/selectors/modulesSelector.ts new file mode 100644 index 0000000000..9ccc15fbf7 --- /dev/null +++ b/app/client/src/ce/selectors/modulesSelector.ts @@ -0,0 +1,7 @@ +/* eslint-disable @typescript-eslint/no-unused-vars */ +import type { AppState } from "@appsmith/reducers"; +import type { Module } from "@appsmith/constants/ModuleConstants"; + +export const getAllModules = ( + state: AppState, +): Record | any => {}; diff --git a/app/client/src/ce/utils/actionExecutionUtils.ts b/app/client/src/ce/utils/actionExecutionUtils.ts index 66d492ee7b..c19892c55c 100644 --- a/app/client/src/ce/utils/actionExecutionUtils.ts +++ b/app/client/src/ce/utils/actionExecutionUtils.ts @@ -1,4 +1,5 @@ import type { Action } from "entities/Action"; +import { ActionExecutionContext } from "entities/Action"; import type { JSAction, JSCollection } from "entities/JSCollection"; import type { ApplicationPayload } from "@appsmith/constants/ReduxActionConstants"; import store from "store"; @@ -65,6 +66,7 @@ export function getActionExecutionAnalytics( isMock: !!datasource?.isMock, actionId: action?.id, inputParams: Object.keys(params).length, + source: ActionExecutionContext.EVALUATION_ACTION_TRIGGER, // Used in analytic events to understand who triggered action execution }; if (!!currentApp) { diff --git a/app/client/src/ce/utils/analyticsUtilTypes.ts b/app/client/src/ce/utils/analyticsUtilTypes.ts index 00c1de8705..2d4a0dd553 100644 --- a/app/client/src/ce/utils/analyticsUtilTypes.ts +++ b/app/client/src/ce/utils/analyticsUtilTypes.ts @@ -354,7 +354,8 @@ export type EventName = | CUSTOM_WIDGET_EVENTS | "MULTI_FILE_PICKER_EXCEEDS_LIMIT" | "TEMPLATE_ADD_PAGE_FROM_TEMPLATE_FLOW" - | HOMEPAGE_CREATE_APP_FROM_TEMPLATE_EVENTS; + | HOMEPAGE_CREATE_APP_FROM_TEMPLATE_EVENTS + | "EDITOR_MODE_CHANGE"; type HOMEPAGE_CREATE_APP_FROM_TEMPLATE_EVENTS = | "TEMPLATE_DROPDOWN_CLICK" @@ -384,7 +385,8 @@ export type ONBOARDING_FLOW_EVENTS = | "ONBOARDING_FLOW_CLICK_SKIP_BUTTON_START_FROM_DATA_PAGE" | "ONBOARDING_FLOW_CLICK_SKIP_BUTTON_DATASOURCE_FORM_PAGE" | "ONBOARDING_FLOW_CLICK_SKIP_BUTTON_START_FROM_TEMPLATE_PAGE" - | "ONBOARDING_FLOW_CLICK_SKIP_BUTTON_TEMPLATE_DETAILS_PAGE"; + | "ONBOARDING_FLOW_CLICK_SKIP_BUTTON_TEMPLATE_DETAILS_PAGE" + | "CODE_MODE_WIDGET_SELECTION"; export type DATASOURCE_SCHEMA_EVENTS = | "DATASOURCE_SCHEMA_SEARCH" diff --git a/app/client/src/components/editorComponents/ActionCreator/helpers.tsx b/app/client/src/components/editorComponents/ActionCreator/helpers.tsx index d67db141bc..6b96ebc666 100644 --- a/app/client/src/components/editorComponents/ActionCreator/helpers.tsx +++ b/app/client/src/components/editorComponents/ActionCreator/helpers.tsx @@ -1,4 +1,3 @@ -import type { ReactNode } from "react"; import React from "react"; import { getFunctionNameFromJsObjectExpression, @@ -20,7 +19,7 @@ import { PluginType } from "entities/Action"; import type { JSAction, Variable } from "entities/JSCollection"; import keyBy from "lodash/keyBy"; import { getActionConfig } from "pages/Editor/Explorer/Actions/helpers"; -import { EntityIcon, JsFileIconV2 } from "pages/Editor/Explorer/ExplorerIcons"; +import { JsFileIconV2 } from "pages/Editor/Explorer/ExplorerIcons"; import { useMemo } from "react"; import { useDispatch, useSelector } from "react-redux"; import type { @@ -66,11 +65,13 @@ import { selectEvaluationVersion } from "@appsmith/selectors/applicationSelector import { isJSAction } from "@appsmith/workers/Evaluation/evaluationUtils"; import type { DataTreeEntity } from "entities/DataTree/dataTreeTypes"; import type { ModuleInstanceDataState } from "@appsmith/constants/ModuleInstanceConstants"; -import { MODULE_TYPE } from "@appsmith/constants/ModuleConstants"; import { setShowCreateNewModal } from "actions/propertyPaneActions"; import { setIdeEditorViewMode } from "actions/ideActions"; import { EditorViewMode } from "@appsmith/entities/IDE/constants"; import { getIsSideBySideEnabled } from "selectors/ideSelectors"; +import { resolveIcon } from "pages/Editor/utils"; +import { getAllModules } from "@appsmith/selectors/modulesSelector"; +import type { Module } from "@appsmith/constants/ModuleConstants"; const actionList: { label: string; @@ -393,16 +394,6 @@ export function useModalDropdownList(handleClose: () => void) { return finalList; } -export const getModuleInstanceIcon = (type: MODULE_TYPE): ReactNode => { - if (type === MODULE_TYPE.QUERY || type === MODULE_TYPE.JS) { - return ( - - - - ); - } -}; - export function getApiQueriesAndJSActionOptionsWithChildren( pageId: string, plugins: any, @@ -412,6 +403,7 @@ export function getApiQueriesAndJSActionOptionsWithChildren( handleClose: () => void, queryModuleInstances: ModuleInstanceDataState, jsModuleInstances: ReturnType, + modules: Record, ) { // this function gets a list of all the queries/apis and attaches it to actionList getApiAndQueryOptions( @@ -420,6 +412,7 @@ export function getApiQueriesAndJSActionOptionsWithChildren( dispatch, handleClose, queryModuleInstances, + modules, ); // this function gets a list of all the JS Objects and attaches it to actionList @@ -434,6 +427,7 @@ function getApiAndQueryOptions( dispatch: any, handleClose: () => void, queryModuleInstances: ModuleInstanceDataState, + modules: Record, ) { const state = store.getState(); const isSideBySideEnabled = getIsSideBySideEnabled(state); @@ -499,12 +493,17 @@ function getApiAndQueryOptions( } as TreeDropdownOption); }); queryModuleInstances.forEach((instance) => { + const module = modules[instance.config.sourceModuleId]; (queryOptions.children as TreeDropdownOption[]).push({ label: instance.config.name, id: instance.config.id, value: instance.config.name, type: queryOptions.value, - icon: getModuleInstanceIcon(instance.config.type), + icon: resolveIcon({ + iconLocation: plugins[module.pluginId]?.iconLocation || "", + pluginType: module.pluginType, + moduleType: module.type, + }), } as TreeDropdownOption); }); } @@ -587,7 +586,7 @@ export function getJSOptions( id: jsModuleInstance.config.id, value: jsModuleInstance.name, type: jsOption.value, - icon: getModuleInstanceIcon(MODULE_TYPE.JS), + icon: JsFileIconV2(), } as unknown as TreeDropdownOption; (jsOption.children as unknown as TreeDropdownOption[]).push(jsObject); @@ -637,6 +636,7 @@ export function useApisQueriesAndJsActionOptions(handleClose: () => void) { getQueryModuleInstances, ) as unknown as ModuleInstanceDataState; const jsModuleInstancesData = useSelector(getJSModuleInstancesData); + const modules = useSelector(getAllModules); // this function gets all the Queries/API's/JS Objects and attaches it to actionList return getApiQueriesAndJSActionOptionsWithChildren( @@ -648,5 +648,6 @@ export function useApisQueriesAndJsActionOptions(handleClose: () => void) { handleClose, queryModuleInstances, jsModuleInstancesData, + modules, ); } diff --git a/app/client/src/components/editorComponents/ActionRightPane/index.tsx b/app/client/src/components/editorComponents/ActionRightPane/index.tsx index 7c6a68d857..386787d0eb 100644 --- a/app/client/src/components/editorComponents/ActionRightPane/index.tsx +++ b/app/client/src/components/editorComponents/ActionRightPane/index.tsx @@ -58,6 +58,17 @@ const SideBar = styled.div` } `; +const Wrapper = styled.div` + border-left: 1px solid var(--ads-v2-color-border); + padding: 0 var(--ads-v2-spaces-7) var(--ads-v2-spaces-4); + overflow: hidden; + border-bottom: 0; + display: flex; + width: ${(props) => props.theme.actionSidePane.width}px; + margin-top: 10px; + /* margin-left: var(--ads-v2-spaces-7); */ +`; + export function useEntityDependencies(actionName: string) { const deps = useSelector((state: AppState) => state.evaluations.dependencies); const entityDependencies = useMemo( @@ -90,16 +101,18 @@ function ActionSidebar({ } return ( - - {actionRightPaneBackLink} - - {additionalSections && ( - - {additionalSections} - - )} - - + + + {actionRightPaneBackLink} + + {additionalSections && ( + + {additionalSections} + + )} + + + ); } diff --git a/app/client/src/components/editorComponents/GlobalSearch/utils.tsx b/app/client/src/components/editorComponents/GlobalSearch/utils.tsx index c30156ba38..d012c47e8b 100644 --- a/app/client/src/components/editorComponents/GlobalSearch/utils.tsx +++ b/app/client/src/components/editorComponents/GlobalSearch/utils.tsx @@ -269,6 +269,7 @@ export interface ActionOperation { focusEntityType?: FocusEntity; dsName?: string; entityExplorerTitle?: string; + isBeta?: boolean; } export const actionOperations: ActionOperation[] = [ diff --git a/app/client/src/components/editorComponents/WidgetQueryGeneratorForm/CommonControls/DatasourceDropdown/useSource/useConnectToOptions.tsx b/app/client/src/components/editorComponents/WidgetQueryGeneratorForm/CommonControls/DatasourceDropdown/useSource/useConnectToOptions.tsx index 17d202093a..ceb84035ed 100644 --- a/app/client/src/components/editorComponents/WidgetQueryGeneratorForm/CommonControls/DatasourceDropdown/useSource/useConnectToOptions.tsx +++ b/app/client/src/components/editorComponents/WidgetQueryGeneratorForm/CommonControls/DatasourceDropdown/useSource/useConnectToOptions.tsx @@ -18,8 +18,6 @@ import type { ActionData, ActionDataState, } from "@appsmith/reducers/entityReducers/actionsReducer"; -import { EntityIcon } from "pages/Editor/Explorer/ExplorerIcons"; -import { Icon } from "design-system"; import type { ModuleInstanceData, ModuleInstanceDataState, @@ -27,6 +25,11 @@ import type { import { selectFeatureFlagCheck } from "@appsmith/selectors/featureFlagsSelectors"; import { FEATURE_FLAG } from "@appsmith/entities/FeatureFlag"; import type { AppState } from "@appsmith/reducers"; +import type { Module } from "@appsmith/constants/ModuleConstants"; +import { getAllModules } from "@appsmith/selectors/modulesSelector"; +import { resolveIcon } from "pages/Editor/utils"; +import { Icon } from "design-system"; +import { EntityIcon } from "pages/Editor/Explorer/ExplorerIcons"; enum SortingWeights { alphabetical = 1, @@ -97,8 +100,25 @@ interface ConnectToOptionsProps { export const getQueryIcon = ( query: ActionData | ModuleInstanceData, pluginImages: Record, + modules: Record, ) => { - if (!query.config.hasOwnProperty("sourceModuleId")) { + if (query.config.hasOwnProperty("type")) { + const q = query as ModuleInstanceData; + const module = modules[q.config.sourceModuleId]; + const icon = resolveIcon({ + iconLocation: pluginImages[module.pluginId] || "", + pluginType: module.pluginType, + moduleType: module.type, + }); + + return ( + icon || ( + + + + ) + ); + } else { const action = query as ActionData; return ( @@ -109,12 +129,6 @@ export const getQueryIcon = ( /> ); - } else { - return ( - - - - ); } }; @@ -172,6 +186,7 @@ function useConnectToOptions(props: ConnectToOptionsProps) { const { pluginImages, widget } = props; const queryModuleInstances = useSelector(getQueryModuleInstances); + const modules = useSelector(getAllModules); let filteredQueries: ActionData[] | ModuleInstanceData[] = queries; /* Exclude Gsheets from query options till this gets resolved https://github.com/appsmithorg/appsmith/issues/27102*/ @@ -193,7 +208,7 @@ function useConnectToOptions(props: ConnectToOptionsProps) { id: query.config.id, label: query.config.name, value: getBindingValue(widget, query), - icon: getQueryIcon(query, pluginImages), + icon: getQueryIcon(query, pluginImages, modules), onSelect: function (value?: string, valueOption?: DropdownOptionType) { addBinding( valueOption?.value, diff --git a/app/client/src/components/propertyControls/ActionSelectorControl.tsx b/app/client/src/components/propertyControls/ActionSelectorControl.tsx index 9ee92ede1f..ef4a73e6ac 100644 --- a/app/client/src/components/propertyControls/ActionSelectorControl.tsx +++ b/app/client/src/components/propertyControls/ActionSelectorControl.tsx @@ -32,6 +32,7 @@ import type { } from "@appsmith/constants/ModuleInstanceConstants"; import { MODULE_TYPE } from "@appsmith/constants/ModuleConstants"; import type { JSAction } from "entities/JSCollection"; +import { getAllModules } from "@appsmith/selectors/modulesSelector"; class ActionSelectorControl extends BaseControl { componentRef = React.createRef(); @@ -108,6 +109,7 @@ class ActionSelectorControl extends BaseControl { const moduleInstances = getModuleInstances(state); const queryModuleInstances = [] as ModuleInstanceDataState; const jsModuleInstances = getJSModuleInstancesData(state); + const modules = getAllModules(state); if (!!moduleInstances) { for (const moduleInstance of Object.values(moduleInstances)) { @@ -166,6 +168,7 @@ class ActionSelectorControl extends BaseControl { }, queryModuleInstances, jsModuleInstances, + modules, ); try { diff --git a/app/client/src/components/utils/NameEditorComponent.tsx b/app/client/src/components/utils/NameEditorComponent.tsx index 9156cef65d..47c55d5e8a 100644 --- a/app/client/src/components/utils/NameEditorComponent.tsx +++ b/app/client/src/components/utils/NameEditorComponent.tsx @@ -34,7 +34,7 @@ export const NameWrapper = styled.div<{ enableFontStyling?: boolean }>` }` : null} - & .t--action-name-edit-field, & .t--js-action-name-edit-field { + & .t--action-name-edit-field, & .t--js-action-name-edit-field, & .t--module-instance-name-edit-field { width: 100%; & > span { diff --git a/app/client/src/constants/ThirdPartyConstants.tsx b/app/client/src/constants/ThirdPartyConstants.tsx index f03e68f827..f98268edb0 100644 --- a/app/client/src/constants/ThirdPartyConstants.tsx +++ b/app/client/src/constants/ThirdPartyConstants.tsx @@ -31,6 +31,8 @@ export const DOCS_BRANCH_PROTECTION_URL = "https://docs.appsmith.com/advanced-concepts/version-control-with-git/working-with-branches#branch-protection"; export const DOCS_DEFAULT_BRANCH_URL = "https://docs.appsmith.com/advanced-concepts/version-control-with-git/working-with-branches#default-branch"; +export const PACKAGES_OVERVIEW_DOC = + "https://docs.appsmith.com/packages/overview"; export const PRICING_PAGE_URL = ( URL: string, diff --git a/app/client/src/ee/pages/Editor/gitSync/useReconnectModalData.ts b/app/client/src/ee/pages/Editor/gitSync/useReconnectModalData.ts new file mode 100644 index 0000000000..d111bbe2f1 --- /dev/null +++ b/app/client/src/ee/pages/Editor/gitSync/useReconnectModalData.ts @@ -0,0 +1,3 @@ +export * from "ce/pages/Editor/gitSync/useReconnectModalData"; +import { default as useCEReconnectModalData } from "ce/pages/Editor/gitSync/useReconnectModalData"; +export default useCEReconnectModalData; diff --git a/app/client/src/ee/selectors/modulesSelector.ts b/app/client/src/ee/selectors/modulesSelector.ts new file mode 100644 index 0000000000..cbfc9be79f --- /dev/null +++ b/app/client/src/ee/selectors/modulesSelector.ts @@ -0,0 +1 @@ +export * from "ce/selectors/modulesSelector"; diff --git a/app/client/src/entities/Action/index.ts b/app/client/src/entities/Action/index.ts index 54b3066456..bea5f25a53 100644 --- a/app/client/src/entities/Action/index.ts +++ b/app/client/src/entities/Action/index.ts @@ -75,6 +75,18 @@ export enum ActionCreationSourceTypeEnum { COPY_ACTION = "COPY_ACTION", } +// Used for analytic events +export enum ActionExecutionContext { + SELF = "SELF", + ONE_CLICK_BINDING = "ONE_CLICK_BINDING", + GENERATE_CRUD_PAGE = "GENERATE_CRUD_PAGE", + CLONE_PAGE = "CLONE_PAGE", + FORK_TEMPLATE_PAGE = "FORK_TEMPLATE_PAGE", + PAGE_LOAD = "PAGE_LOAD", + EVALUATION_ACTION_TRIGGER = "EVALUATION_ACTION_TRIGGER", + REFRESH_ACTIONS_ON_ENV_CHANGE = "REFRESH_ACTIONS_ON_ENV_CHANGE", +} + export interface KeyValuePair { key?: string; value?: unknown; diff --git a/app/client/src/layoutSystems/common/draggable/DraggableComponent.tsx b/app/client/src/layoutSystems/common/draggable/DraggableComponent.tsx index 86d78353ef..05f4725940 100644 --- a/app/client/src/layoutSystems/common/draggable/DraggableComponent.tsx +++ b/app/client/src/layoutSystems/common/draggable/DraggableComponent.tsx @@ -20,13 +20,13 @@ import { getShouldAllowDrag } from "selectors/widgetDragSelectors"; import { combinedPreviewModeSelector } from "selectors/editorSelectors"; import { getAnvilSpaceDistributionStatus } from "layoutSystems/anvil/integrations/selectors"; -const DraggableWrapper = styled.div` +const DraggableWrapper = styled.div<{ draggable: boolean }>` display: block; flex-direction: column; width: 100%; height: 100%; user-select: none; - cursor: grab; + cursor: ${(props) => (props.draggable ? "grab" : "unset")}; `; export interface DraggableComponentProps { @@ -37,7 +37,7 @@ export interface DraggableComponentProps { type: string; children: ReactNode; generateDragState: ( - e: React.DragEvent, + e: React.DragEvent, draggableRef: HTMLElement, ) => SetDraggingStateActionPayload; dragDisabled: boolean; @@ -53,7 +53,6 @@ const WidgetBoundaries = styled.div` ${(props) => getColorWithOpacity(props.theme.colors.textAnchor, 0.5)}; pointer-events: none; top: 0; - position: absolute; left: 0; `; @@ -100,14 +99,14 @@ function DraggableComponent(props: DraggableComponentProps) { !props.isFlexChild && (isCurrentWidgetDragging || isDraggingSibling); // When mouse is over this draggable - const handleMouseOver = (e: any) => { + const handleMouseOver = (e: React.MouseEvent) => { focusWidget && !isResizingOrDragging && !isFocused && !isDistributingSpace && !props.resizeDisabled && !isPreviewMode && - focusWidget(props.widgetId); + focusWidget(props.widgetId, e.metaKey); e.stopPropagation(); }; diff --git a/app/client/src/layoutSystems/common/dropTarget/DropTargetComponent.tsx b/app/client/src/layoutSystems/common/dropTarget/DropTargetComponent.tsx index 9639be084c..846dc4c1a8 100644 --- a/app/client/src/layoutSystems/common/dropTarget/DropTargetComponent.tsx +++ b/app/client/src/layoutSystems/common/dropTarget/DropTargetComponent.tsx @@ -40,6 +40,7 @@ import { useCurrentAppState } from "pages/Editor/IDE/hooks"; import { getIsAppSettingsPaneWithNavigationTabOpen } from "selectors/appSettingsPaneSelectors"; import { getLayoutSystemType } from "selectors/layoutSystemSelectors"; import { useFeatureFlag } from "utils/hooks/useFeatureFlag"; +import { getWidgetSelectionBlock } from "selectors/ui"; import { isAutoHeightEnabledForWidget, isAutoHeightEnabledForWidgetWithLimits, @@ -259,6 +260,7 @@ export function DropTargetComponent(props: DropTargetComponentProps) { ); // Are we changing the auto height limits by dragging the signifiers? const { isAutoHeightWithLimitsChanging } = useAutoHeightUIState(); + const isWidgetSelectionBlocked = useSelector(getWidgetSelectionBlock); const dispatch = useDispatch(); @@ -327,7 +329,12 @@ export function DropTargetComponent(props: DropTargetComponentProps) { (e.target as HTMLDivElement).dataset.testid === selectionDiv || (e.target as HTMLDivElement).dataset.testid === mainCanvasId; - if (!isResizing && !isDragging && !isAutoHeightWithLimitsChanging) { + if ( + !isResizing && + !isDragging && + !isAutoHeightWithLimitsChanging && + !isWidgetSelectionBlocked + ) { // Check if Target is the MainCanvas if (isTargetMainCanvas) { goToWidgetAdd(); diff --git a/app/client/src/layoutSystems/common/resizer/ModalResizableLayer.tsx b/app/client/src/layoutSystems/common/resizer/ModalResizableLayer.tsx index ffe88063ef..ad5b71af17 100644 --- a/app/client/src/layoutSystems/common/resizer/ModalResizableLayer.tsx +++ b/app/client/src/layoutSystems/common/resizer/ModalResizableLayer.tsx @@ -23,6 +23,7 @@ import { combinedPreviewModeSelector, snipingModeSelector, } from "selectors/editorSelectors"; +import { getWidgetSelectionBlock } from "../../../selectors/ui"; const minSize = 100; /** @@ -101,7 +102,9 @@ export const ModalResizableLayer = ({ }; const isPreviewMode = useSelector(combinedPreviewModeSelector); const isSnipingMode = useSelector(snipingModeSelector); - const enableResizing = !isSnipingMode && !isPreviewMode; + const isWidgetSelectionBlocked = useSelector(getWidgetSelectionBlock); + const enableResizing = + !isSnipingMode && !isPreviewMode && !isWidgetSelectionBlocked; return ( ` - .${Classes.POPOVER_TARGET} { - height: 100%; - } -`; + const WidgetNameBoundary = 1; const BORDER_RADIUS = 4; const SettingsWrapper = styled.div<{ widgetWidth: number; inverted: boolean }>` @@ -60,10 +54,6 @@ const WidgetName = styled.span` white-space: nowrap; `; -const StyledErrorIcon = styled(Icon)` - margin-right: ${(props) => props.theme.spaces[1]}px; -`; - interface SettingsControlProps { toggleSettings: (e: any) => void; activity: Activities; @@ -111,17 +101,17 @@ const getStyles = ( export function SettingsControl(props: SettingsControlProps) { const isSnipingMode = useSelector(snipingModeSelector); - const errorIcon = ; + const errorIcon = ; return ( - + {isSnipingMode ? `Bind to widget ${props.name}` : `Edit widget`} + } - hoverOpenDelay={500} - position="top-right" + mouseEnterDelay={0} + placement="topRight" > - + ); } diff --git a/app/client/src/layoutSystems/fixedlayout/editor/FixedLayoutCanvasArenas/CanvasSelectionArena.tsx b/app/client/src/layoutSystems/fixedlayout/editor/FixedLayoutCanvasArenas/CanvasSelectionArena.tsx index ccde7e6ba3..3bb3653d1f 100644 --- a/app/client/src/layoutSystems/fixedlayout/editor/FixedLayoutCanvasArenas/CanvasSelectionArena.tsx +++ b/app/client/src/layoutSystems/fixedlayout/editor/FixedLayoutCanvasArenas/CanvasSelectionArena.tsx @@ -30,6 +30,7 @@ import { getAbsolutePixels } from "utils/helpers"; import type { XYCord } from "layoutSystems/common/canvasArenas/ArenaTypes"; import { useCanvasDragToScroll } from "layoutSystems/common/canvasArenas/useCanvasDragToScroll"; import { StickyCanvasArena } from "layoutSystems/common/canvasArenas/StickyCanvasArena"; +import { getWidgetSelectionBlock } from "../../../../selectors/ui"; export interface SelectedArenaDimensions { top: number; @@ -71,6 +72,7 @@ export function CanvasSelectionArena({ ); const appMode = useSelector(getAppMode); const isPreviewMode = useSelector(combinedPreviewModeSelector); + const isWidgetSelectionBlocked = useSelector(getWidgetSelectionBlock); const isAppSettingsPaneWithNavigationTabOpen = useSelector( getIsAppSettingsPaneWithNavigationTabOpen, ); @@ -501,6 +503,7 @@ export function CanvasSelectionArena({ !( isDragging || isPreviewMode || + isWidgetSelectionBlocked || isAppSettingsPaneWithNavigationTabOpen || dropDisabled ); diff --git a/app/client/src/pages/Editor/APIEditor/CommonEditorForm.tsx b/app/client/src/pages/Editor/APIEditor/CommonEditorForm.tsx index eacb7df5a0..303a162a62 100644 --- a/app/client/src/pages/Editor/APIEditor/CommonEditorForm.tsx +++ b/app/client/src/pages/Editor/APIEditor/CommonEditorForm.tsx @@ -644,102 +644,107 @@ function CommonEditorForm(props: CommonFormPropsWithExtraParams) { )} - - - - - - {Object.values(API_EDITOR_TABS).map((tab) => ( - - {createMessage(API_EDITOR_TAB_TITLES[tab])} - - ))} - - - - - - - - - - - - {props.bodyUIComponent} - - - {props.paginationUIComponent} - - - - - - - + + + + + + {Object.values(API_EDITOR_TABS).map((tab) => ( + + {createMessage(API_EDITOR_TAB_TITLES[tab])} + + ))} + + + + + - - - - - - + + + + + + + {props.bodyUIComponent} + + + {props.paginationUIComponent} + + + + + + + + + + + + + + ; @@ -65,6 +67,12 @@ function ApiEditorWrapper(props: ApiEditorWrapperProps) { const isConverting = useSelector((state) => getIsActionConverting(state, action?.id || ""), ); + const pluginGroups = useMemo(() => keyBy(plugins, "id"), [plugins]); + const icon = resolveIcon({ + iconLocation: pluginGroups[pluginId]?.iconLocation || "", + pluginType: action?.pluginType || "", + moduleType: action?.actionConfiguration?.body?.moduleType, + }) || ; const isChangePermitted = getHasManageActionPermission( isFeatureEnabled, @@ -150,7 +158,7 @@ function ApiEditorWrapper(props: ApiEditorWrapperProps) { const notification = useMemo(() => { if (!isConverting) return null; - return ; + return ; }, [action?.name, isConverting]); return ( diff --git a/app/client/src/pages/Editor/Canvas.tsx b/app/client/src/pages/Editor/Canvas.tsx index 1b024f7939..87faf621f3 100644 --- a/app/client/src/pages/Editor/Canvas.tsx +++ b/app/client/src/pages/Editor/Canvas.tsx @@ -18,6 +18,7 @@ import { CANVAS_ART_BOARD } from "constants/componentClassNameConstants"; import { renderAppsmithCanvas } from "layoutSystems/CanvasFactory"; import type { WidgetProps } from "widgets/BaseWidget"; import { getAppThemeSettings } from "@appsmith/selectors/applicationSelectors"; +import CodeModeTooltip from "pages/Editor/WidgetsEditor/CodeModeTooltip"; interface CanvasProps { widgetsStructure: CanvasWidgetStructure; @@ -83,20 +84,22 @@ const Canvas = (props: CanvasProps) => { const renderChildren = () => { return ( - - {props.widgetsStructure.widgetId && - renderAppsmithCanvas(props.widgetsStructure as WidgetProps)} - + + + {props.widgetsStructure.widgetId && + renderAppsmithCanvas(props.widgetsStructure as WidgetProps)} + + ); }; diff --git a/app/client/src/pages/Editor/Explorer/ExplorerIcons.tsx b/app/client/src/pages/Editor/Explorer/ExplorerIcons.tsx index 848b38974b..e1c760a333 100644 --- a/app/client/src/pages/Editor/Explorer/ExplorerIcons.tsx +++ b/app/client/src/pages/Editor/Explorer/ExplorerIcons.tsx @@ -337,21 +337,3 @@ export function AppsmithAIIcon() { export function ActionUrlIcon(url: string) { return ; } - -export function ModuleIcon( - height = 18, - width = 18, - noBackground = false, - noBorder = false, -) { - return ( - - - - ); -} diff --git a/app/client/src/pages/Editor/IDE/EditorPane/PagesSection.tsx b/app/client/src/pages/Editor/IDE/EditorPane/PagesSection.tsx index d6669f43a3..d13268dc9c 100644 --- a/app/client/src/pages/Editor/IDE/EditorPane/PagesSection.tsx +++ b/app/client/src/pages/Editor/IDE/EditorPane/PagesSection.tsx @@ -102,6 +102,7 @@ const PagesSection = () => { style={springs} > { + const localStorageFlag = + localStorage.getItem(LOCAL_STORAGE_KEYS.SPLITPANE_ANNOUNCEMENT) || "true"; + const [show, setShow] = useState(JSON.parse(localStorageFlag)); + + const tryClickHandler = () => { + setShow(false); + localStorage.setItem(LOCAL_STORAGE_KEYS.SPLITPANE_ANNOUNCEMENT, "false"); + }; + + const learnClickHandler = () => { + window.open( + "https://community.appsmith.com/content/blog/discover-ide-20-building-more-efficient-ide", + "_blank", + ); + }; + + const modalFooter = () => ( + <> + + + + ); + + return ( + + ); +}; + +export { Announcement }; diff --git a/app/client/src/pages/Editor/IDE/EditorPane/components/Pages.tsx b/app/client/src/pages/Editor/IDE/EditorPane/components/Pages.tsx deleted file mode 100644 index de876e62cf..0000000000 --- a/app/client/src/pages/Editor/IDE/EditorPane/components/Pages.tsx +++ /dev/null @@ -1,17 +0,0 @@ -import React from "react"; -import { useSelector } from "react-redux"; -import { default as OldPages } from "pages/Editor/Explorer/Pages"; -import { PagesSection } from "../PagesSection"; -import { getIsSideBySideEnabled } from "selectors/ideSelectors"; - -const Pages = () => { - const isSideBySideEnabled = useSelector(getIsSideBySideEnabled); - - if (!isSideBySideEnabled) { - return ; - } else { - return ; - } -}; - -export { Pages }; diff --git a/app/client/src/pages/Editor/IDE/EditorPane/components/SegmentedHeader.tsx b/app/client/src/pages/Editor/IDE/EditorPane/components/SegmentedHeader.tsx index c65805f011..6bc5bff456 100644 --- a/app/client/src/pages/Editor/IDE/EditorPane/components/SegmentedHeader.tsx +++ b/app/client/src/pages/Editor/IDE/EditorPane/components/SegmentedHeader.tsx @@ -1,4 +1,4 @@ -import React from "react"; +import React, { useCallback } from "react"; import { Button, Flex, SegmentedControl, Tooltip } from "design-system"; import { createMessage, @@ -19,6 +19,7 @@ import { useFeatureFlag } from "utils/hooks/useFeatureFlag"; import { FEATURE_FLAG } from "@appsmith/entities/FeatureFlag"; import { getIDEViewMode, getIsSideBySideEnabled } from "selectors/ideSelectors"; import { setIdeEditorViewMode } from "actions/ideActions"; +import AnalyticsUtil from "../../../../../utils/AnalyticsUtil"; const Container = styled(Flex)` #editor-pane-segment-control { @@ -44,6 +45,12 @@ const SegmentedHeader = () => { }; const { segment } = useCurrentEditorState(); const { onSegmentChange } = useSegmentNavigation(); + const handleMaximizeButtonClick = useCallback(() => { + AnalyticsUtil.logEvent("EDITOR_MODE_CHANGE", { + to: EditorViewMode.FullScreen, + }); + dispatch(setIdeEditorViewMode(EditorViewMode.FullScreen)); + }, []); return ( { id="editor-mode-maximize" isIconButton kind="tertiary" - onClick={() => - dispatch(setIdeEditorViewMode(EditorViewMode.FullScreen)) - } + onClick={handleMaximizeButtonClick} startIcon="maximize-v3" /> diff --git a/app/client/src/pages/Editor/IDE/EditorPane/index.tsx b/app/client/src/pages/Editor/IDE/EditorPane/index.tsx index d2529b38b8..7003f66dcd 100644 --- a/app/client/src/pages/Editor/IDE/EditorPane/index.tsx +++ b/app/client/src/pages/Editor/IDE/EditorPane/index.tsx @@ -9,7 +9,7 @@ import EditorPaneSegments from "./EditorPaneSegments"; import GlobalAdd from "./GlobalAdd"; import { useEditorPaneWidth } from "../hooks"; import EntityProperties from "pages/Editor/Explorer/Entity/EntityProperties"; -import { Pages } from "./components/Pages"; +import { PagesSection } from "./PagesSection"; const EditorPane = ({ match: { path } }: RouteComponentProps) => { const width = useEditorPaneWidth(); @@ -26,7 +26,7 @@ const EditorPane = ({ match: { path } }: RouteComponentProps) => { {/** Entity Properties component is needed to render the Bindings popover in the context menu. Will be removed eventually **/} - + diff --git a/app/client/src/pages/Editor/IDE/EditorTabs/FullScreenTabs.tsx b/app/client/src/pages/Editor/IDE/EditorTabs/FullScreenTabs.tsx index 3f33cfd921..7fcc979a4b 100644 --- a/app/client/src/pages/Editor/IDE/EditorTabs/FullScreenTabs.tsx +++ b/app/client/src/pages/Editor/IDE/EditorTabs/FullScreenTabs.tsx @@ -18,6 +18,7 @@ import { MINIMIZE_BUTTON_TOOLTIP, createMessage, } from "@appsmith/constants/messages"; +import AnalyticsUtil from "utils/AnalyticsUtil"; const FullScreenTabs = () => { const dispatch = useDispatch(); @@ -26,6 +27,9 @@ const FullScreenTabs = () => { const { segment } = useCurrentEditorState(); const setSplitScreenMode = useCallback(() => { dispatch(setIdeEditorViewMode(EditorViewMode.SplitScreen)); + AnalyticsUtil.logEvent("EDITOR_MODE_CHANGE", { + to: EditorViewMode.SplitScreen, + }); }, []); const tabsConfig = TabSelectors[segment]; const pageId = useSelector(getCurrentPageId); diff --git a/app/client/src/pages/Editor/IDE/EditorTabs/SplitScreenTabs.tsx b/app/client/src/pages/Editor/IDE/EditorTabs/SplitScreenTabs.tsx index 3f5559d846..eefaec4130 100644 --- a/app/client/src/pages/Editor/IDE/EditorTabs/SplitScreenTabs.tsx +++ b/app/client/src/pages/Editor/IDE/EditorTabs/SplitScreenTabs.tsx @@ -19,6 +19,7 @@ import { getCurrentPageId } from "@appsmith/selectors/entitiesSelector"; import history, { NavigationMethod } from "utils/history"; import { includes } from "lodash"; import ListButton from "./ListButton"; +import { Announcement } from "../EditorPane/components/Announcement"; const SplitScreenTabs = () => { const isSideBySideEnabled = useSelector(getIsSideBySideEnabled); @@ -53,18 +54,23 @@ const SplitScreenTabs = () => { if (!isSideBySideEnabled) return null; if (ideViewMode === EditorViewMode.FullScreen) return null; if (segment === EditorEntityTab.UI) return null; - return files.length > 0 ? ( - - - - - - ) : null; + return ( + <> + {files.length > 0 ? ( + + + + + + ) : null} + + + ); }; export default SplitScreenTabs; diff --git a/app/client/src/pages/Editor/IDE/Header/EditorTitle.tsx b/app/client/src/pages/Editor/IDE/Header/EditorTitle.tsx index fd0d162e03..1361474410 100644 --- a/app/client/src/pages/Editor/IDE/Header/EditorTitle.tsx +++ b/app/client/src/pages/Editor/IDE/Header/EditorTitle.tsx @@ -32,6 +32,7 @@ const EditorTitle = ({ title }: { title: string }) => { { const pageId = useSelector(getCurrentPageId) as string; const currentPage = useSelector(getPageById(pageId)); const appState = useCurrentAppState(); + const isSaving = useSelector(getIsPageSaving); + const pageSaveError = useSelector(getPageSavingError); // states const [isPopoverOpen, setIsPopoverOpen] = useState(false); @@ -202,7 +206,6 @@ const Header = () => { className={"t--editor-header"} height={"40px"} overflow={"hidden"} - px={"spaces-4"} width={"100%"} > { gap={"spaces-4"} height={"100%"} justifyContent={"left"} + pl={"spaces-4"} > + { height={"100%"} justifyContent={"center"} > - - - {currentWorkspace.name && ( - <> - - {currentWorkspace.name + " / "} - - el.id === applicationId) - .length > 0 - } - isPopoverOpen={isPopoverOpen} - onBlur={(value: string) => - updateApplicationDispatch(applicationId || "", { - name: value, - currentApp: true, - }) - } - setIsPopoverOpen={setIsPopoverOpen} - /> - - )} - - + + {currentWorkspace.name && ( + <> + + {currentWorkspace.name + " / "} + + el.id === applicationId) + .length > 0 + } + isPopoverOpen={isPopoverOpen} + onBlur={(value: string) => + updateApplicationDispatch(applicationId || "", { + name: value, + currentApp: true, + }) + } + setIsPopoverOpen={setIsPopoverOpen} + /> + + )} + + {props.title} {props.rightIcon ? props.rightIcon : null} diff --git a/app/client/src/pages/Editor/IDE/MainPane/index.tsx b/app/client/src/pages/Editor/IDE/MainPane/index.tsx index bd2a5040b5..2f679302f5 100644 --- a/app/client/src/pages/Editor/IDE/MainPane/index.tsx +++ b/app/client/src/pages/Editor/IDE/MainPane/index.tsx @@ -4,11 +4,13 @@ import { Route, Switch, useRouteMatch } from "react-router"; import * as Sentry from "@sentry/react"; import useRoutes from "@appsmith/pages/Editor/IDE/MainPane/useRoutes"; import EditorTabs from "pages/Editor/IDE/EditorTabs/FullScreenTabs"; +import { useWidgetSelectionBlockListener } from "pages/Editor/IDE/hooks"; const SentryRoute = Sentry.withSentryRouting(Route); export const MainPane = (props: { id: string }) => { const { path } = useRouteMatch(); const routes = useRoutes(path); + useWidgetSelectionBlockListener(); return (
{ const [appState, setAppState] = useState(EditorState.EDITOR); @@ -215,3 +217,41 @@ export const useIsEditorPaneSegmentsEnabled = () => { return isEditorSegmentsReleaseEnabled || isEditorSegmentsRolloutEnabled; }; + +export function useWidgetSelectionBlockListener() { + const { pathname } = useLocation(); + const dispatch = useDispatch(); + const currentFocus = identifyEntityFromPath(pathname); + const isAltFocused = useSelector(getIsAltFocusWidget); + const widgetSelectionIsBlocked = useSelector(getWidgetSelectionBlock); + + useEffect(() => { + const inUIMode = [ + FocusEntity.CANVAS, + FocusEntity.PROPERTY_PANE, + FocusEntity.WIDGET_LIST, + ].includes(currentFocus.entity); + dispatch(setWidgetSelectionBlock(!inUIMode)); + }, [currentFocus]); + + useEffect(() => { + window.addEventListener("keydown", handleKeyDown); + window.addEventListener("keyup", handleKeyUp); + + return () => { + window.removeEventListener("keydown", handleKeyDown); + window.removeEventListener("keyup", handleKeyUp); + }; + }, [isAltFocused, widgetSelectionIsBlocked]); + const handleKeyDown = (e: KeyboardEvent) => { + if (!isAltFocused && widgetSelectionIsBlocked && e.metaKey) { + dispatch(altFocusWidget(e.metaKey)); + } + }; + + const handleKeyUp = (e: KeyboardEvent) => { + if (!e.metaKey && widgetSelectionIsBlocked) { + dispatch(altFocusWidget(e.metaKey)); + } + }; +} diff --git a/app/client/src/pages/Editor/QueryEditor/EditorJSONtoForm.tsx b/app/client/src/pages/Editor/QueryEditor/EditorJSONtoForm.tsx index 3434429581..c56a291325 100644 --- a/app/client/src/pages/Editor/QueryEditor/EditorJSONtoForm.tsx +++ b/app/client/src/pages/Editor/QueryEditor/EditorJSONtoForm.tsx @@ -3,13 +3,7 @@ import React, { useCallback } from "react"; import type { InjectedFormProps } from "redux-form"; import { noop } from "lodash"; import type { Datasource } from "entities/Datasource"; -import { getPluginNameFromId } from "@appsmith/selectors/entitiesSelector"; -import { - PluginName, - type Action, - type QueryAction, - type SaaSAction, -} from "entities/Action"; +import type { Action, QueryAction, SaaSAction } from "entities/Action"; import { useDispatch, useSelector } from "react-redux"; import ActionSettings from "pages/Editor/ActionSettings"; import { Button, Tab, TabPanel, Tabs, TabsList, Tooltip } from "design-system"; @@ -23,9 +17,7 @@ import { import { useParams } from "react-router"; import type { AppState } from "@appsmith/reducers"; import { thinScrollbar } from "constants/DefaultTheme"; -import ActionRightPane, { - useEntityDependencies, -} from "components/editorComponents/ActionRightPane"; +import ActionRightPane from "components/editorComponents/ActionRightPane"; import type { ActionResponse } from "api/ActionAPI"; import type { Plugin } from "api/PluginApi"; import type { UIComponentTypes } from "api/PluginApi"; @@ -134,17 +126,6 @@ const DocumentationButton = styled(Button)` z-index: 6; `; -const SidebarWrapper = styled.div<{ show: boolean }>` - border-left: 1px solid var(--ads-v2-color-border); - padding: 0 var(--ads-v2-spaces-7) var(--ads-v2-spaces-4); - overflow: hidden; - border-bottom: 0; - display: ${(props) => (props.show ? "flex" : "none")}; - width: ${(props) => props.theme.actionSidePane.width}px; - margin-top: 10px; - /* margin-left: var(--ads-v2-spaces-7); */ -`; - export const SegmentedControlContainer = styled.div` padding: 0 var(--ads-v2-spaces-7); padding-top: var(--ads-v2-spaces-4); @@ -234,13 +215,6 @@ export function EditorJSONtoForm(props: Props) { FEATURE_FLAG.release_actions_redesign_enabled, ); - const showRightPane = Boolean(actionRightPaneAdditionSections); - - // get the current action's plugin name - const currentActionPluginName = useSelector((state: AppState) => - getPluginNameFromId(state, currentActionConfig?.pluginId || ""), - ); - const dispatch = useDispatch(); const handleDocumentationClick = () => { @@ -254,21 +228,12 @@ export function EditorJSONtoForm(props: Props) { id: currentActionConfig ? currentActionConfig.id : "", }; - const { hasDependencies } = useEntityDependencies(props.actionName); - const selectedConfigTab = useSelector(getQueryPaneConfigSelectedTabIndex); const setSelectedConfigTab = useCallback((selectedIndex: string) => { dispatch(setQueryPaneConfigSelectedTabIndex(selectedIndex)); }, []); - // here we check for normal conditions for opening action pane - // or if any of the flags are true, We should open the actionpane by default. - const shouldOpenActionPaneByDefault = - hasDependencies || - !!actionResponse || - currentActionPluginName !== PluginName.SMTP; - // when switching between different redux forms, make sure this redux form has been initialized before rendering anything. // the initialized prop below comes from redux-form. if (!props.initialized) { @@ -419,14 +384,10 @@ export function EditorJSONtoForm(props: Props) { />
- {showRightPane && ( - - - - )} +
diff --git a/app/client/src/pages/Editor/QueryEditor/index.tsx b/app/client/src/pages/Editor/QueryEditor/index.tsx index 9b593f6a72..e7c90460a7 100644 --- a/app/client/src/pages/Editor/QueryEditor/index.tsx +++ b/app/client/src/pages/Editor/QueryEditor/index.tsx @@ -19,6 +19,7 @@ import { DatasourceCreateEntryPoints } from "constants/Datasource"; import { getAction, getIsActionConverting, + getPluginImages, getPluginSettingConfigs, } from "@appsmith/selectors/entitiesSelector"; import { integrationEditorURL } from "@appsmith/RouteBuilder"; @@ -38,6 +39,8 @@ import { MODULE_TYPE } from "@appsmith/constants/ModuleConstants"; import ConvertEntityNotification from "@appsmith/pages/common/ConvertEntityNotification"; import { PluginType } from "entities/Action"; import { useIsEditorPaneSegmentsEnabled } from "../IDE/hooks"; +import { Icon } from "design-system"; +import { resolveIcon } from "../utils"; type QueryEditorProps = RouteComponentProps; @@ -58,6 +61,12 @@ function QueryEditor(props: QueryEditorProps) { const isConverting = useSelector((state) => getIsActionConverting(state, actionId || ""), ); + const pluginImages = useSelector(getPluginImages); + const icon = resolveIcon({ + iconLocation: pluginImages[pluginId] || "", + pluginType: action?.pluginType || "", + moduleType: action?.actionConfiguration?.body?.moduleType, + }) || ; const isDeletePermitted = getHasDeleteActionPermission( isFeatureEnabled, @@ -156,7 +165,13 @@ function QueryEditor(props: QueryEditorProps) { const notification = useMemo(() => { if (!isConverting) return null; - return ; + return ( + + ); }, [action?.name, isConverting]); return ( diff --git a/app/client/src/pages/Editor/ThemePropertyPane/SaveThemeModal.tsx b/app/client/src/pages/Editor/ThemePropertyPane/SaveThemeModal.tsx deleted file mode 100644 index f8b67ad7f6..0000000000 --- a/app/client/src/pages/Editor/ThemePropertyPane/SaveThemeModal.tsx +++ /dev/null @@ -1,178 +0,0 @@ -import React, { useState } from "react"; -import { useDispatch, useSelector } from "react-redux"; - -import AnalyticsUtil from "utils/AnalyticsUtil"; -import { saveSelectedThemeAction } from "actions/appThemingActions"; -import { getCurrentApplicationId } from "selectors/editorSelectors"; -import { getAppThemes } from "selectors/appThemingSelectors"; -import { - createMessage, - ERROR_MESSAGE_NAME_EMPTY, - APLHANUMERIC_HYPHEN_SLASH_SPACE_ERROR, - UNIQUE_NAME_ERROR, -} from "@appsmith/constants/messages"; -import { - Button, - Input, - Text, - Modal, - ModalContent, - ModalHeader, - ModalFooter, - ModalBody, -} from "design-system"; - -interface SaveThemeModalProps { - isOpen: boolean; - onClose(): void; -} - -function SaveThemeModal(props: SaveThemeModalProps) { - const { isOpen } = props; - const dispatch = useDispatch(); - const [name, setName] = useState(""); - const [inputValidator, setInputValidator] = useState({ - isValid: false, - message: "", - isDirty: false, - }); - const applicationId = useSelector(getCurrentApplicationId); - const themes = useSelector(getAppThemes); - - /** - * dispatches action to save selected theme - * - */ - const onSubmit = (event: any) => { - event.preventDefault(); - - // if input validations fails, don't do anything - if (!inputValidator.isValid || inputValidator.isDirty === false) return; - - AnalyticsUtil.logEvent("APP_THEMING_SAVE_THEME_SUCCESS", { - themeName: name, - }); - - dispatch(saveSelectedThemeAction({ applicationId, name })); - - // close the modal after submit - onClose(); - }; - - /** - * theme creation validator - * - * @param value - * @returns - */ - const createThemeValidator = (value: string) => { - let isValid = !!value; - - let errorMessage = !isValid ? createMessage(ERROR_MESSAGE_NAME_EMPTY) : ""; - - if ( - isValid && - themes.find((theme) => value.toLowerCase() === theme.name.toLowerCase()) - ) { - isValid = false; - errorMessage = createMessage(UNIQUE_NAME_ERROR); - } - - if (/[^a-zA-Z0-9\-\/\ ]/.test(value)) { - isValid = false; - errorMessage = createMessage(APLHANUMERIC_HYPHEN_SLASH_SPACE_ERROR); - } - - return { - isValid: isValid, - message: errorMessage, - isDirty: true, - }; - }; - - /** - * on input change - * - * @param value - */ - const onChangeName = (value: string) => { - const validator = createThemeValidator(value); - - setInputValidator(validator); - setName(value); - }; - - /** - * on close modal - */ - const onClose = () => { - // reset validations - setInputValidator({ - isValid: false, - message: "", - isDirty: false, - }); - - props.onClose(); - }; - - return ( - { - if (!isOpen) { - onClose(); - } - }} - open={isOpen} - > - { - e.preventDefault(); - }} - style={{ width: "640px" }} - > - Save theme - -
- - You can save your custom themes to use across applications and use - them when you need. - -
- -
-
-
- -
- - -
-
-
-
- ); -} - -export default SaveThemeModal; diff --git a/app/client/src/pages/Editor/ThemePropertyPane/ThemeEditor.tsx b/app/client/src/pages/Editor/ThemePropertyPane/ThemeEditor.tsx index 3cab5935d5..635ddbcabc 100644 --- a/app/client/src/pages/Editor/ThemePropertyPane/ThemeEditor.tsx +++ b/app/client/src/pages/Editor/ThemePropertyPane/ThemeEditor.tsx @@ -1,7 +1,7 @@ import styled, { createGlobalStyle } from "styled-components"; import { get, startCase } from "lodash"; import { useDispatch, useSelector } from "react-redux"; -import React, { useCallback, useState } from "react"; +import React, { useCallback } from "react"; import ThemeCard from "./ThemeCard"; import { @@ -15,7 +15,6 @@ import { updateSelectedAppThemeAction, } from "actions/appThemingActions"; import SettingSection from "./SettingSection"; -import SaveThemeModal from "./SaveThemeModal"; import type { AppTheme } from "entities/AppTheming"; import AnalyticsUtil from "utils/AnalyticsUtil"; import ThemeFontControl from "./controls/ThemeFontControl"; @@ -64,7 +63,6 @@ function ThemeEditor() { const applicationId = useSelector(getCurrentApplicationId); const selectedTheme = useSelector(getSelectedAppTheme); const themingStack = useSelector(getAppThemingStack); - const [isSaveModalOpen, setSaveModalOpen] = useState(false); /** * customizes the current theme @@ -95,22 +93,6 @@ function ThemeEditor() { ); }, [setAppThemingModeStackAction]); - /** - * open the save modal - */ - const onOpenSaveModal = useCallback(() => { - AnalyticsUtil.logEvent("APP_THEMING_SAVE_THEME_START"); - - setSaveModalOpen(true); - }, [setSaveModalOpen]); - - /** - * on close save modal - */ - const onCloseSaveModal = useCallback(() => { - setSaveModalOpen(false); - }, [setSaveModalOpen]); - /** * resets theme */ @@ -136,9 +118,6 @@ function ThemeEditor() { /> - - Save theme - Reset widget styles @@ -270,7 +249,6 @@ function ThemeEditor() { )} - ); diff --git a/app/client/src/pages/Editor/WidgetsEditor/CodeModeTooltip.tsx b/app/client/src/pages/Editor/WidgetsEditor/CodeModeTooltip.tsx new file mode 100644 index 0000000000..9c1e2e8a17 --- /dev/null +++ b/app/client/src/pages/Editor/WidgetsEditor/CodeModeTooltip.tsx @@ -0,0 +1,36 @@ +import { Tooltip } from "design-system"; +import React, { useEffect, useState } from "react"; +import { modText } from "utils/helpers"; +import { useSelector } from "react-redux"; +import { getWidgetSelectionBlock } from "selectors/ui"; +import { retrieveCodeWidgetNavigationUsed } from "utils/storage"; + +const CodeModeTooltip = (props: { children: React.ReactElement }) => { + const isWidgetSelectionBlock = useSelector(getWidgetSelectionBlock); + const [shouldShow, setShouldShow] = useState(false); + useEffect(() => { + retrieveCodeWidgetNavigationUsed() + .then((timesUsed) => { + if (timesUsed < 2) { + setShouldShow(true); + } + }) + .catch(() => { + setShouldShow(true); + }); + }, [isWidgetSelectionBlock]); + if (!isWidgetSelectionBlock) return props.children; + return ( + + {props.children} + + ); +}; + +export default CodeModeTooltip; diff --git a/app/client/src/pages/Editor/gitSync/ImportedAppSuccessModal.tsx b/app/client/src/pages/Editor/gitSync/ImportSuccessModal.tsx similarity index 73% rename from app/client/src/pages/Editor/gitSync/ImportedAppSuccessModal.tsx rename to app/client/src/pages/Editor/gitSync/ImportSuccessModal.tsx index 7ac850e4a1..9aa6cd56f9 100644 --- a/app/client/src/pages/Editor/gitSync/ImportedAppSuccessModal.tsx +++ b/app/client/src/pages/Editor/gitSync/ImportSuccessModal.tsx @@ -27,8 +27,17 @@ const StyledModalContent = styled(ModalContent)` width: 640px; `; -function ImportedApplicationSuccessModal() { - const importedAppSuccess = localStorage.getItem("importApplicationSuccess"); +interface ImportSuccessModalProps { + title?: string; + description?: string; +} + +function ImportSuccessModal(props: ImportSuccessModalProps) { + const { + description = createMessage(APPLICATION_IMPORT_SUCCESS_DESCRIPTION), + title = createMessage(APPLICATION_IMPORT_SUCCESS), + } = props; + const importedAppSuccess = localStorage.getItem("importSuccess"); // const isOpen = importedAppSuccess === "true"; const [isOpen, setIsOpen] = useState(importedAppSuccess === "true"); @@ -40,7 +49,7 @@ function ImportedApplicationSuccessModal() { const close = () => { setIsOpen(false); - localStorage.setItem("importApplicationSuccess", "false"); + localStorage.setItem("importSuccess", "false"); }; return ( @@ -54,10 +63,8 @@ function ImportedApplicationSuccessModal() { name="success" size={"lg"} /> - - {createMessage(APPLICATION_IMPORT_SUCCESS)} - - {createMessage(APPLICATION_IMPORT_SUCCESS_DESCRIPTION)} + {title} + {description} @@ -76,4 +83,4 @@ function ImportedApplicationSuccessModal() { ); } -export default ImportedApplicationSuccessModal; +export default ImportSuccessModal; diff --git a/app/client/src/pages/Editor/gitSync/ReconnectDatasourceModal.tsx b/app/client/src/pages/Editor/gitSync/ReconnectDatasourceModal.tsx index f1e791a4f5..25fd58eb90 100644 --- a/app/client/src/pages/Editor/gitSync/ReconnectDatasourceModal.tsx +++ b/app/client/src/pages/Editor/gitSync/ReconnectDatasourceModal.tsx @@ -19,9 +19,7 @@ import { RECONNECT_DATASOURCE_SUCCESS_MESSAGE1, RECONNECT_DATASOURCE_SUCCESS_MESSAGE2, RECONNECT_MISSING_DATASOURCE_CREDENTIALS, - RECONNECT_MISSING_DATASOURCE_CREDENTIALS_DESCRIPTION, SKIP_CONFIGURATION, - SKIP_TO_APPLICATION, SKIP_TO_APPLICATION_TOOLTIP_DESCRIPTION, } from "@appsmith/constants/messages"; import { @@ -51,7 +49,6 @@ import { getOAuthAccessToken, loadFilePickerAction, } from "actions/datasourceActions"; -import { builderURL } from "@appsmith/RouteBuilder"; import localStorage from "utils/localStorage"; import { Modal, @@ -76,6 +73,9 @@ import { import type { AppState } from "@appsmith/reducers"; import { getFetchedWorkspaces } from "@appsmith/selectors/workspaceSelectors"; import { getApplicationsOfWorkspace } from "@appsmith/selectors/selectedWorkspaceSelectors"; +import useReconnectModalData from "@appsmith/pages/Editor/gitSync/useReconnectModalData"; +import { resetImportData } from "@appsmith/actions/workspaceActions"; +import history from "utils/history"; const Section = styled.div` display: flex; @@ -289,7 +289,6 @@ function ReconnectDatasourceModal() { >(queryDatasourceId); const [pageId, setPageId] = useState(queryPageId); const [appId, setAppId] = useState(queryAppId); - const [appURL, setAppURL] = useState(""); const [datasource, setDatasource] = useState(null); const [isImport, setIsImport] = useState(queryIsImport); const [isTesting, setIsTesting] = useState(false); @@ -312,6 +311,21 @@ function ReconnectDatasourceModal() { return output; }; + /** + * The role of useReconnectModalData is to provide editorId (appId or packageId), parentEntityId (pageId or moduleId) + * and any differentiating elements when a app vs package is imported. + * Right now it takes the pageId and appId and returns editorId/parentEntityId to reduces the changes required to + * refactor this for packages. Ideally the hook should calculate everything and return the necessary values. + */ + const { + editorId, + editorType, + editorURL, + missingDsCredentialsDescription, // pageId or moduleId + parentEntityId, // appId or packageId from query params + skipMessage, + } = useReconnectModalData({ pageId, appId }); + // when redirecting from oauth, processing the status if (isImport) { setIsImport(false); @@ -333,6 +347,7 @@ function ReconnectDatasourceModal() { workspaceId: orgId, datasourceName: dsName, pluginName: plugins[datasource?.pluginId || ""]?.name, + editorType, }); } else if (queryDatasourceId) { dispatch(loadFilePickerAction()); @@ -348,7 +363,7 @@ function ReconnectDatasourceModal() { if (app) { dispatch( setWorkspaceIdForImport({ - editorId: appId || "", + editorId: editorId || "", workspaceId: app.workspaceId, }), ); @@ -363,7 +378,7 @@ function ReconnectDatasourceModal() { dispatch({ type: ReduxActionTypes.FETCH_UNCONFIGURED_DATASOURCE_LIST, payload: { - applicationId: appId, + applicationId: editorId, workspaceId: app.workspaceId, }, }); @@ -428,15 +443,20 @@ function ReconnectDatasourceModal() { } }; + const clearImportData = () => { + dispatch(resetImportData()); + }; + const onClose = () => { localStorage.setItem("importedAppPendingInfo", "null"); dispatch(setIsReconnectingDatasourcesModalOpen({ isOpen: false })); dispatch( - setWorkspaceIdForImport({ editorId: appId || "", workspaceId: "" }), + setWorkspaceIdForImport({ editorId: editorId || "", workspaceId: "" }), ); dispatch(setPageIdForImport("")); dispatch(resetDatasourceConfigForImportFetchedFlag()); setSelectedDatasourceId(""); + clearImportData(); }; const onSelectDatasource = useCallback((ds: Datasource) => { @@ -478,17 +498,6 @@ function ReconnectDatasourceModal() { } }, [importedApplication, queryIsImport]); - useEffect(() => { - if (pageId) { - // TODO: Update route params here - setAppURL( - builderURL({ - pageId: pageId, - }), - ); - } - }, [pageId]); - // checking of full configured useEffect(() => { if (isModalOpen && !isTesting) { @@ -524,14 +533,14 @@ function ReconnectDatasourceModal() { } // When datasources are present and pending datasources are 0, // then only we want to update status as success - else if (appURL && pending.length === 0 && datasources.length > 0) { + else if (editorURL && pending.length === 0 && datasources.length > 0) { // open application import successfule - localStorage.setItem("importApplicationSuccess", "true"); + localStorage.setItem("importSuccess", "true"); localStorage.setItem("importedAppPendingInfo", "null"); - window.open(appURL, "_self"); + window.open(editorURL, "_self"); } } - }, [datasources, appURL, isModalOpen, isTesting, queryIsImport]); + }, [datasources, editorURL, isModalOpen, isTesting, queryIsImport]); const mappedDataSources = datasources.map((ds: Datasource) => { return ( @@ -551,6 +560,13 @@ function ReconnectDatasourceModal() { const shouldShowDBForm = isConfigFetched && !isLoading && !checkIfDatasourceIsConfigured(datasource); + const onSkipBtnClick = () => { + AnalyticsUtil.logEvent("RECONNECTING_SKIP_TO_APPLICATION_BUTTON_CLICK"); + localStorage.setItem("importedAppPendingInfo", "null"); + editorURL && history.push(editorURL); + onClose(); + }; + return ( - - {createMessage( - RECONNECT_MISSING_DATASOURCE_CREDENTIALS_DESCRIPTION, - )} - + {missingDsCredentialsDescription} {mappedDataSources} {shouldShowDBForm && ( )} {checkIfDatasourceIsConfigured(datasource) && SuccessMessages()} @@ -599,18 +611,12 @@ function ReconnectDatasourceModal() { diff --git a/app/client/src/pages/Editor/gitSync/components/GitChangesList.tsx b/app/client/src/pages/Editor/gitSync/components/GitChangesList.tsx index 011417885c..1d4002cef7 100644 --- a/app/client/src/pages/Editor/gitSync/components/GitChangesList.tsx +++ b/app/client/src/pages/Editor/gitSync/components/GitChangesList.tsx @@ -57,6 +57,8 @@ export enum Kind { JS_LIB = "JS_LIB", THEME = "THEME", SETTINGS = "SETTINGS", + PACKAGES = "PACKAGES", + MODULES = "MODULES", } interface GitStatusProps { @@ -125,6 +127,22 @@ const STATUS_MAP: GitStatusMap = { iconName: "package", hasValue: (status?.modifiedJSLibs || 0) > 0, }), + [Kind.PACKAGES]: (status) => ({ + message: `${status?.modifiedPackages || 0} ${ + (status?.modifiedPackages || 0) <= 1 ? "package" : "packages" + } modified`, + iconName: "package", + hasValue: (status?.modifiedPackages || 0) > 0, + }), + [Kind.MODULES]: (status) => ({ + message: `${status?.modifiedModules || 0} ${ + (status?.modifiedModules || 0) <= 1 + ? "module configuration" + : "module configurations" + } modified`, + iconName: "package", + hasValue: (status?.modifiedModules || 0) > 0, + }), }; function behindCommitMessage(status: Partial) { @@ -193,6 +211,8 @@ export function gitChangeListData( Kind.JS_OBJECT, Kind.DATA_SOURCE, Kind.JS_LIB, + Kind.MODULES, + Kind.PACKAGES, ]; return changeKind .map((type: Kind) => STATUS_MAP[type](status)) diff --git a/app/client/src/pages/Editor/index.tsx b/app/client/src/pages/Editor/index.tsx index 1f43b5dfbe..366a6b8d2f 100644 --- a/app/client/src/pages/Editor/index.tsx +++ b/app/client/src/pages/Editor/index.tsx @@ -30,7 +30,7 @@ import { setupPage, updateCurrentPage } from "actions/pageActions"; import { getCurrentPageId } from "selectors/editorSelectors"; import { getSearchQuery } from "utils/helpers"; import RepoLimitExceededErrorModal from "./gitSync/RepoLimitExceededErrorModal"; -import ImportedApplicationSuccessModal from "./gitSync/ImportedAppSuccessModal"; +import ImportedApplicationSuccessModal from "./gitSync/ImportSuccessModal"; import { getIsBranchUpdated } from "../utils"; import { APP_MODE } from "entities/App"; import { GIT_BRANCH_QUERY_KEY } from "constants/routes"; diff --git a/app/client/src/pages/Editor/utils.ts b/app/client/src/pages/Editor/utils.tsx similarity index 88% rename from app/client/src/pages/Editor/utils.ts rename to app/client/src/pages/Editor/utils.tsx index 84529bad59..03597d3b22 100644 --- a/app/client/src/pages/Editor/utils.ts +++ b/app/client/src/pages/Editor/utils.tsx @@ -1,7 +1,8 @@ -import { debounce, random } from "lodash"; -import { useEffect, useMemo, useState } from "react"; +import React from "react"; import ReactDOM from "react-dom"; +import { useEffect, useMemo, useState } from "react"; import { useLocation } from "react-router"; +import { debounce, random } from "lodash"; import type { WidgetCardsGroupedByTags, WidgetTags, @@ -19,6 +20,15 @@ import { useSelector } from "react-redux"; import { getCurrentPageId } from "selectors/editorSelectors"; import type { WidgetCardProps } from "widgets/BaseWidget"; import type { ActionResponse } from "api/ActionAPI"; +import { MODULE_TYPE } from "@appsmith/constants/ModuleConstants"; +import { + ENTITY_ICON_SIZE, + EntityIcon, + JsFileIconV2, + dbQueryIcon, +} from "pages/Editor/Explorer/ExplorerIcons"; +import { PluginType } from "entities/Action"; +import { getAssetUrl } from "@appsmith/utils/airgapHelpers"; export const draggableElement = ( id: string, @@ -336,3 +346,38 @@ export const actionResponseDisplayDataFormats = ( responseDisplayFormat, }; }; + +function resolveQueryModuleIcon( + iconLocation: string, + pluginType: string, + isLargeIcon: boolean, +) { + if (iconLocation) + return ( + + entityIcon + + ); + else if (pluginType === PluginType.DB) return dbQueryIcon; +} + +export function resolveIcon({ + iconLocation, + isLargeIcon = false, + moduleType, + pluginType, +}: { + iconLocation: string; + pluginType: string; + moduleType: string; + isLargeIcon?: boolean; +}) { + if (moduleType === MODULE_TYPE.JS) { + return isLargeIcon ? JsFileIconV2(34, 34) : JsFileIconV2(16, 16); + } else { + return resolveQueryModuleIcon(iconLocation, pluginType, isLargeIcon); + } +} diff --git a/app/client/src/reducers/uiReducers/appThemingReducer.ts b/app/client/src/reducers/uiReducers/appThemingReducer.ts index af37ad8338..c26b40ff3d 100644 --- a/app/client/src/reducers/uiReducers/appThemingReducer.ts +++ b/app/client/src/reducers/uiReducers/appThemingReducer.ts @@ -111,12 +111,6 @@ const themeReducer = createImmerReducer(initialState, { (theme) => theme.id !== action.payload.themeId, ); }, - [ReduxActionTypes.SAVE_APP_THEME_SUCCESS]: ( - state: AppThemingState, - action: ReduxAction, - ) => { - state.themes.push(action.payload); - }, [ReduxActionTypes.UPDATE_BETA_CARD_SHOWN]: ( state: AppThemingState, action: ReduxAction, diff --git a/app/client/src/reducers/uiReducers/dragResizeReducer.ts b/app/client/src/reducers/uiReducers/dragResizeReducer.ts index fb41c9872f..dd52089a0c 100644 --- a/app/client/src/reducers/uiReducers/dragResizeReducer.ts +++ b/app/client/src/reducers/uiReducers/dragResizeReducer.ts @@ -22,6 +22,8 @@ const initialState: WidgetDragResizeState = { isDistributingSpace: false, }, isDraggingDisabled: false, + blockSelection: false, + altFocus: false, }; export const widgetDraggingReducer = createImmerReducer(initialState, { @@ -100,11 +102,20 @@ export const widgetDraggingReducer = createImmerReducer(initialState, { }, [ReduxActionTypes.FOCUS_WIDGET]: ( state: WidgetDragResizeState, - action: ReduxAction<{ widgetId?: string }>, + action: ReduxAction<{ widgetId?: string; alt?: boolean }>, ) => { if (state.focusedWidget !== action.payload.widgetId) { state.focusedWidget = action.payload.widgetId; } + if (state.altFocus !== action.payload.alt) { + state.altFocus = !!action.payload.alt; + } + }, + [ReduxActionTypes.ALT_FOCUS_WIDGET]: ( + state: WidgetDragResizeState, + action: ReduxAction, + ) => { + state.altFocus = action.payload; }, [ReduxActionTypes.SET_SELECTED_WIDGET_ANCESTRY]: ( state: WidgetDragResizeState, @@ -118,6 +129,12 @@ export const widgetDraggingReducer = createImmerReducer(initialState, { ) => { state.entityExplorerAncestry = action.payload; }, + [ReduxActionTypes.SET_WIDGET_SELECTION_BLOCK]: ( + state: WidgetDragResizeState, + action: ReduxAction, + ) => { + state.blockSelection = action.payload; + }, //space distribution redux [AnvilReduxActionTypes.ANVIL_SPACE_DISTRIBUTION_START]: ( state: WidgetDragResizeState, @@ -166,6 +183,8 @@ export interface WidgetDragResizeState { selectedWidgets: string[]; isAutoCanvasResizing: boolean; isDraggingDisabled: boolean; + blockSelection: boolean; + altFocus: boolean; } export default widgetDraggingReducer; diff --git a/app/client/src/reducers/uiReducers/gitSyncReducer.ts b/app/client/src/reducers/uiReducers/gitSyncReducer.ts index 5c28324c38..b69a7b9f06 100644 --- a/app/client/src/reducers/uiReducers/gitSyncReducer.ts +++ b/app/client/src/reducers/uiReducers/gitSyncReducer.ts @@ -670,6 +670,9 @@ export interface GitStatusData { modifiedJSLibs: number; discardDocUrl?: string; migrationMessage?: string; + modifiedPackages?: number; + modifiedModules?: number; + modifiedModuleInstances?: number; } interface GitErrorPayloadType { diff --git a/app/client/src/sagas/ActionExecution/PluginActionSaga.ts b/app/client/src/sagas/ActionExecution/PluginActionSaga.ts index 83f4c7c43f..eb683cdce6 100644 --- a/app/client/src/sagas/ActionExecution/PluginActionSaga.ts +++ b/app/client/src/sagas/ActionExecution/PluginActionSaga.ts @@ -9,6 +9,7 @@ import { } from "redux-saga/effects"; import * as Sentry from "@sentry/react"; import type { updateActionDataPayloadType } from "actions/pluginActionActions"; +import { executePageLoadActions } from "actions/pluginActionActions"; import { clearActionResponse, executePluginActionError, @@ -77,6 +78,7 @@ import { import type { EventName } from "@appsmith/utils/analyticsUtilTypes"; import AnalyticsUtil from "utils/AnalyticsUtil"; import type { Action } from "entities/Action"; +import { ActionExecutionContext } from "entities/Action"; import { PluginType } from "entities/Action"; import LOG_TYPE from "entities/AppsmithConsole/logtype"; import { @@ -742,6 +744,7 @@ export function* runActionSaga( paginationField?: PaginationField; skipOpeningDebugger: boolean; action?: Action; + actionExecutionContext?: ActionExecutionContext; }>, ) { const span = startRootSpan("runActionSaga"); @@ -956,14 +959,7 @@ export function* runActionSaga( show: false, }, }); - let failureEventName: EventName = "RUN_API_FAILURE"; - if (actionObject.pluginType === PluginType.DB) { - failureEventName = "RUN_QUERY_FAILURE"; - } - if (actionObject.pluginType === PluginType.SAAS) { - failureEventName = "RUN_SAAS_API_FAILURE"; - } - AnalyticsUtil.logEvent(failureEventName, { + AnalyticsUtil.logEvent("EXECUTE_ACTION_FAILURE", { actionId, actionName: pluginActionNameToDisplay, environmentId: currentEnvDetails.id, @@ -975,19 +971,12 @@ export function* runActionSaga( isMock: !!datasource?.isMock, actionConfig: actionAnalyticsPayload, ...payload?.pluginErrorDetails, + source: reduxAction.payload.actionExecutionContext, }); return; } - let eventName: EventName = "RUN_API"; - if (actionObject.pluginType === PluginType.DB) { - eventName = "RUN_QUERY"; - } - if (actionObject.pluginType === PluginType.SAAS) { - eventName = "RUN_SAAS_API"; - } - - AnalyticsUtil.logEvent(eventName, { + AnalyticsUtil.logEvent("EXECUTE_ACTION", { actionId, actionName: pluginActionNameToDisplay, environmentId: currentEnvDetails.id, @@ -999,6 +988,7 @@ export function* runActionSaga( pluginName: plugin?.name, isMock: !!datasource?.isMock, actionConfig: actionAnalyticsPayload, + source: reduxAction.payload.actionExecutionContext, }); yield put({ @@ -1100,7 +1090,11 @@ function* executeOnPageLoadJSAction(pageAction: PageAction) { } } -function* executePageLoadAction(pageAction: PageAction, span?: OtlpSpan) { +function* executePageLoadAction( + pageAction: PageAction, + span?: OtlpSpan, + actionExecutionContext?: ActionExecutionContext, +) { const currentEnvDetails: { id: string; name: string } = yield select( getCurrentEnvironmentDetails, ); @@ -1137,6 +1131,9 @@ function* executePageLoadAction(pageAction: PageAction, span?: OtlpSpan) { isMock: !!datasource?.isMock, actionId: pageAction?.id, inputParams: 0, + source: !!actionExecutionContext + ? actionExecutionContext + : ActionExecutionContext.PAGE_LOAD, }); const actionName = getPluginActionNameToDisplay( @@ -1247,6 +1244,9 @@ function* executePageLoadAction(pageAction: PageAction, span?: OtlpSpan) { actionId: pageAction?.id, inputParams: 0, ...payload.pluginErrorDetails, + source: !!actionExecutionContext + ? actionExecutionContext + : ActionExecutionContext.PAGE_LOAD, }); } else { AnalyticsUtil.logEvent("EXECUTE_ACTION_SUCCESS", { @@ -1265,6 +1265,9 @@ function* executePageLoadAction(pageAction: PageAction, span?: OtlpSpan) { isMock: !!datasource?.isMock, actionId: pageAction?.id, inputParams: 0, + source: !!actionExecutionContext + ? actionExecutionContext + : ActionExecutionContext.PAGE_LOAD, }); PerformanceTracker.stopAsyncTracking( PerformanceTransactionName.EXECUTE_ACTION, @@ -1285,7 +1288,11 @@ function* executePageLoadAction(pageAction: PageAction, span?: OtlpSpan) { } } -function* executePageLoadActionsSaga() { +function* executePageLoadActionsSaga( + actionPayload: ReduxAction<{ + actionExecutionContext?: ActionExecutionContext; + }>, +) { const span = startRootSpan("executePageLoadActionsSaga"); try { const pageActions: PageAction[][] = yield select(getLayoutOnLoadActions); @@ -1305,7 +1312,12 @@ function* executePageLoadActionsSaga() { // @ts-expect-error: no idea how to type this yield* yield all( actionSet.map((apiAction) => - call(executePageLoadAction, apiAction, span), + call( + executePageLoadAction, + apiAction, + span, + actionPayload.payload.actionExecutionContext, + ), ), ); } @@ -1626,7 +1638,11 @@ function* softRefreshActionsSaga() { // Clear all the action responses on the page yield call(clearTriggerActionResponse); //Rerun all the page load actions on the page - yield call(executePageLoadActionsSaga); + yield put( + executePageLoadActions( + ActionExecutionContext.REFRESH_ACTIONS_ON_ENV_CHANGE, + ), + ); try { // we fork to prevent the call from blocking yield put(softRefreshDatasourceStructure()); diff --git a/app/client/src/sagas/AppThemingSaga.tsx b/app/client/src/sagas/AppThemingSaga.tsx index 92b83d71d0..476e2e1a8f 100644 --- a/app/client/src/sagas/AppThemingSaga.tsx +++ b/app/client/src/sagas/AppThemingSaga.tsx @@ -3,7 +3,6 @@ import type { DeleteAppThemeAction, FetchAppThemesAction, FetchSelectedAppThemeAction, - SaveAppThemeAction, UpdateSelectedAppThemeAction, } from "actions/appThemingActions"; import { updateisBetaCardShownAction } from "actions/appThemingActions"; @@ -19,7 +18,6 @@ import { CHANGE_APP_THEME, createMessage, DELETE_APP_THEME, - SAVE_APP_THEME, SET_DEFAULT_SELECTED_THEME, } from "@appsmith/constants/messages"; import { ENTITY_TYPE } from "@appsmith/entities/AppsmithConsole/utils"; @@ -225,37 +223,6 @@ export function* changeSelectedTheme( } } -/** - * save and create new theme from selected theme - * - * @param action - */ -export function* saveSelectedTheme(action: ReduxAction) { - const { applicationId, name } = action.payload; - - try { - const response: ApiResponse = yield ThemingApi.saveTheme( - applicationId, - { name }, - ); - - yield put({ - type: ReduxActionTypes.SAVE_APP_THEME_SUCCESS, - payload: response.data, - }); - - // shows toast - toast.show(createMessage(SAVE_APP_THEME, name), { - kind: "success", - }); - } catch (error) { - yield put({ - type: ReduxActionErrorTypes.SAVE_APP_THEME_ERROR, - payload: { error }, - }); - } -} - /** * deletes custom saved theme * @@ -359,7 +326,6 @@ export default function* appThemingSaga() { ReduxActionTypes.CHANGE_SELECTED_APP_THEME_INIT, changeSelectedTheme, ), - takeLatest(ReduxActionTypes.SAVE_APP_THEME_INIT, saveSelectedTheme), takeLatest(ReduxActionTypes.DELETE_APP_THEME_INIT, deleteTheme), takeLatest(ReduxActionTypes.CLOSE_BETA_CARD_SHOWN, closeisBetaCardShown), takeLatest( diff --git a/app/client/src/sagas/OneClickBindingSaga.ts b/app/client/src/sagas/OneClickBindingSaga.ts index f6d644c279..da4006121c 100644 --- a/app/client/src/sagas/OneClickBindingSaga.ts +++ b/app/client/src/sagas/OneClickBindingSaga.ts @@ -6,6 +6,7 @@ import { import type { Plugin } from "api/PluginApi"; import { ActionCreationSourceTypeEnum, + ActionExecutionContext, PluginType, type Action, type QueryActionConfig, @@ -223,7 +224,15 @@ function* BindWidgetToDatasource( //TODO(Balaji): Need to make changes to plugin saga to execute the actions in parallel for (const actionToRun of actionsToRun) { - yield put(runAction(actionToRun.id, undefined, true)); + yield put( + runAction( + actionToRun.id, + undefined, + true, + undefined, + ActionExecutionContext.ONE_CLICK_BINDING, + ), + ); const runResponse: ReduxAction = yield take([ ReduxActionTypes.RUN_ACTION_SUCCESS, diff --git a/app/client/src/sagas/WidgetSelectionSagas.ts b/app/client/src/sagas/WidgetSelectionSagas.ts index 5b957ffbbf..1fe5dbba35 100644 --- a/app/client/src/sagas/WidgetSelectionSagas.ts +++ b/app/client/src/sagas/WidgetSelectionSagas.ts @@ -24,12 +24,12 @@ import type { CanvasWidgetsReduxState } from "reducers/entityReducers/canvasWidg import { all, call, put, select, take, takeLatest } from "redux-saga/effects"; import type { SetSelectionResult } from "sagas/WidgetSelectUtils"; import { - SelectionRequestType, assertParentId, getWidgetAncestry, isInvalidSelectionRequest, pushPopWidgetSelection, selectAllWidgetsInCanvasSaga, + SelectionRequestType, selectMultipleWidgets, selectOneWidget, shiftSelectWidgets, @@ -41,7 +41,11 @@ import { getIsFetchingPage, snipingModeSelector, } from "selectors/editorSelectors"; -import { getLastSelectedWidget, getSelectedWidgets } from "selectors/ui"; +import { + getLastSelectedWidget, + getSelectedWidgets, + getWidgetSelectionBlock, +} from "selectors/ui"; import { areArraysEqual } from "utils/AppsmithUtils"; import { quickScrollToWidget } from "utils/helpers"; import history, { NavigationMethod } from "utils/history"; @@ -55,6 +59,12 @@ import { getModalWidgetType } from "selectors/widgetSelectors"; import { selectFeatureFlags } from "@appsmith/selectors/featureFlagsSelectors"; import type { FeatureFlags } from "@appsmith/entities/FeatureFlag"; import { getWidgetSelectorByWidgetId } from "selectors/layoutSystemSelectors"; +import { getAppViewerPageIdFromPath } from "@appsmith/pages/Editor/Explorer/helpers"; +import AnalyticsUtil from "../utils/AnalyticsUtil"; +import { + retrieveCodeWidgetNavigationUsed, + storeCodeWidgetNavigationUsed, +} from "../utils/storage"; // The following is computed to be used in the entity explorer // Every time a widget is selected, we need to expand widget entities @@ -67,8 +77,17 @@ function* selectWidgetSaga(action: ReduxAction) { payload = [], selectionRequestType, } = action.payload; + /** + * Apart from the normal selection request by a user on canvas, there are other ways which can trigger selection + * e.g. when a modal closes in the editor -> we select the main container. + * One way modal closes is because user navigates to home page using the appsmith icon. In this case, we don't want the selection process to trigger. + * This also safeguards against the case where the selection process is triggered by a non-canvas click where user moves out of editor. + * */ - if (payload.some(isInvalidSelectionRequest)) { + const isOnEditorURL = !!getAppViewerPageIdFromPath( + window.location.pathname, + ); + if (payload.some(isInvalidSelectionRequest) || !isOnEditorURL) { // Throw error return; } @@ -198,9 +217,16 @@ function* appendSelectedWidgetToUrlSaga( invokedBy?: NavigationMethod, ) { const isSnipingMode: boolean = yield select(snipingModeSelector); + const isWidgetSelectionBlocked: boolean = yield select( + getWidgetSelectionBlock, + ); + const timesUsedCodeModeWidgetSelection: number = yield call( + retrieveCodeWidgetNavigationUsed, + ); const appMode: APP_MODE = yield select(getAppMode); const viewMode = appMode === APP_MODE.PUBLISHED; if (isSnipingMode || viewMode) return; + const { pathname } = window.location; const currentPageId: string = yield select(getCurrentPageId); const currentURL = pathname; @@ -215,6 +241,15 @@ function* appendSelectedWidgetToUrlSaga( persistExistingParams: true, selectedWidgets: [MAIN_CONTAINER_WIDGET_ID], }); + if (invokedBy === NavigationMethod.CanvasClick && isWidgetSelectionBlocked) { + AnalyticsUtil.logEvent("CODE_MODE_WIDGET_SELECTION"); + if (timesUsedCodeModeWidgetSelection < 2) { + yield call( + storeCodeWidgetNavigationUsed, + timesUsedCodeModeWidgetSelection + 1, + ); + } + } if (currentURL !== newUrl) { history.push(newUrl, { invokedBy }); } diff --git a/app/client/src/selectors/gitSyncSelectors.tsx b/app/client/src/selectors/gitSyncSelectors.tsx index d3b6efc307..68c3388953 100644 --- a/app/client/src/selectors/gitSyncSelectors.tsx +++ b/app/client/src/selectors/gitSyncSelectors.tsx @@ -135,8 +135,12 @@ export const getMergeError = (state: AppState) => state.ui.gitSync.mergeError; export const getCountOfChangesToCommit = (state: AppState) => { const gitStatus = getGitStatus(state); - const { modifiedPages = 0, modifiedQueries = 0 } = gitStatus || {}; - return modifiedPages + modifiedQueries; + const { + modifiedModules = 0, + modifiedPages = 0, + modifiedQueries = 0, + } = gitStatus || {}; + return modifiedPages + modifiedQueries + modifiedModules; }; export const getShowRepoLimitErrorModal = (state: AppState) => diff --git a/app/client/src/selectors/ui.tsx b/app/client/src/selectors/ui.tsx index 435410addc..2dfd0bef01 100644 --- a/app/client/src/selectors/ui.tsx +++ b/app/client/src/selectors/ui.tsx @@ -68,3 +68,16 @@ export const getIsImportingCurl = (state: AppState) => export const getIsConsolidatedPageLoading = (state: AppState) => state.ui.consolidatedPageLoad.isLoading; + +export const getIsAltFocusWidget = (state: AppState) => + state.ui.widgetDragResize.altFocus; + +export const getWidgetSelectionBlock = (state: AppState) => + state.ui.widgetDragResize.blockSelection; + +export const getAltBlockWidgetSelection = createSelector( + [getWidgetSelectionBlock, getIsAltFocusWidget], + (isWidgetSelectionBlock, isAltFocusWidget) => { + return isWidgetSelectionBlock ? !isAltFocusWidget : false; + }, +); diff --git a/app/client/src/selectors/widgetDragSelectors.ts b/app/client/src/selectors/widgetDragSelectors.ts index c962998b55..54343cb1cd 100644 --- a/app/client/src/selectors/widgetDragSelectors.ts +++ b/app/client/src/selectors/widgetDragSelectors.ts @@ -5,6 +5,7 @@ import { combinedPreviewModeSelector, snipingModeSelector, } from "./editorSelectors"; +import { getWidgetSelectionBlock } from "./ui"; export const getIsDragging = (state: AppState) => state.ui.widgetDragResize.isDragging; @@ -25,6 +26,7 @@ export const getShouldAllowDrag = createSelector( combinedPreviewModeSelector, snipingModeSelector, getIsAppSettingsPaneWithNavigationTabOpen, + getWidgetSelectionBlock, ( isResizing, isDragging, @@ -32,6 +34,7 @@ export const getShouldAllowDrag = createSelector( isPreviewMode, isSnipingMode, isAppSettingsPaneWithNavigationTabOpen, + widgetSelectionIsBlocked, ) => { return ( !isResizing && @@ -39,7 +42,8 @@ export const getShouldAllowDrag = createSelector( !isDraggingDisabled && !isSnipingMode && !isPreviewMode && - !isAppSettingsPaneWithNavigationTabOpen + !isAppSettingsPaneWithNavigationTabOpen && + !widgetSelectionIsBlocked ); }, ); diff --git a/app/client/src/selectors/widgetSelectors.ts b/app/client/src/selectors/widgetSelectors.ts index 20e64217bb..04144e6586 100644 --- a/app/client/src/selectors/widgetSelectors.ts +++ b/app/client/src/selectors/widgetSelectors.ts @@ -9,6 +9,7 @@ import { getNextEntityName } from "utils/AppsmithUtils"; import WidgetFactory from "WidgetProvider/factory"; import { + getAltBlockWidgetSelection, getFocusedWidget, getLastSelectedWidget, getSelectedWidgets, @@ -179,6 +180,7 @@ export const shouldWidgetIgnoreClicksSelector = (widgetId: string) => { getAppMode, combinedPreviewModeSelector, getIsAutoHeightWithLimitsChanging, + getAltBlockWidgetSelection, ( focusedWidgetId, isTableFilterPaneVisible, @@ -188,6 +190,7 @@ export const shouldWidgetIgnoreClicksSelector = (widgetId: string) => { appMode, isPreviewMode, isAutoHeightWithLimitsChanging, + isWidgetSelectionBlock, ) => { const isFocused = focusedWidgetId === widgetId; @@ -199,7 +202,8 @@ export const shouldWidgetIgnoreClicksSelector = (widgetId: string) => { appMode !== APP_MODE.EDIT || !isFocused || isTableFilterPaneVisible || - isAutoHeightWithLimitsChanging + isAutoHeightWithLimitsChanging || + isWidgetSelectionBlock ); }, ); diff --git a/app/client/src/utils/hooks/useAllowEditorDragToSelect.ts b/app/client/src/utils/hooks/useAllowEditorDragToSelect.ts index 6c1d2e734c..3d36241f26 100644 --- a/app/client/src/utils/hooks/useAllowEditorDragToSelect.ts +++ b/app/client/src/utils/hooks/useAllowEditorDragToSelect.ts @@ -7,6 +7,7 @@ import { useSelector } from "react-redux"; import { getIsAppSettingsPaneWithNavigationTabOpen } from "selectors/appSettingsPaneSelectors"; import { getLayoutSystemType } from "selectors/layoutSystemSelectors"; import { LayoutSystemTypes } from "layoutSystems/types"; +import { getWidgetSelectionBlock } from "../../selectors/ui"; export const useAllowEditorDragToSelect = () => { // This state tells us whether a `ResizableComponent` is resizing @@ -46,6 +47,8 @@ export const useAllowEditorDragToSelect = () => { getIsAppSettingsPaneWithNavigationTabOpen, ); + const isWidgetSelectionBlocked = useSelector(getWidgetSelectionBlock); + return ( isFixedLayout && !isAutoCanvasResizing && @@ -53,6 +56,7 @@ export const useAllowEditorDragToSelect = () => { !isDraggingDisabled && !isSnipingMode && !isPreviewMode && - !isAppSettingsPaneWithNavigationTabOpen + !isAppSettingsPaneWithNavigationTabOpen && + !isWidgetSelectionBlocked ); }; diff --git a/app/client/src/utils/hooks/useWidgetSelection.ts b/app/client/src/utils/hooks/useWidgetSelection.ts index 2d275fd021..23b6a145af 100644 --- a/app/client/src/utils/hooks/useWidgetSelection.ts +++ b/app/client/src/utils/hooks/useWidgetSelection.ts @@ -1,4 +1,4 @@ -import { focusWidget } from "actions/widgetActions"; +import { altFocusWidget, focusWidget } from "actions/widgetActions"; import { selectWidgetInitAction } from "actions/widgetSelectionActions"; import { useCallback } from "react"; @@ -23,7 +23,8 @@ export const useWidgetSelection = () => { [dispatch], ), focusWidget: useCallback( - (widgetId?: string) => dispatch(focusWidget(widgetId)), + (widgetId?: string, altFocus?: boolean) => + dispatch(focusWidget(widgetId, altFocus)), [dispatch], ), deselectAll: useCallback( @@ -38,5 +39,8 @@ export const useWidgetSelection = () => { [dispatch], ), goToWidgetAdd: useCallback(() => history.push(builderURL({})), []), + altFocus: useCallback((alt: boolean) => { + dispatch(altFocusWidget(alt)); + }, []), }; }; diff --git a/app/client/src/utils/localStorage.tsx b/app/client/src/utils/localStorage.tsx index e8fe777f39..9418e33071 100644 --- a/app/client/src/utils/localStorage.tsx +++ b/app/client/src/utils/localStorage.tsx @@ -9,6 +9,7 @@ import { toast } from "design-system"; export const LOCAL_STORAGE_KEYS = { CANVAS_CARDS_STATE: "CANVAS_CARDS_STATE", + SPLITPANE_ANNOUNCEMENT: "SPLITPANE_ANNOUNCEMENT", }; class LocalStorageNotSupportedError extends Error { diff --git a/app/client/src/utils/storage.ts b/app/client/src/utils/storage.ts index a0aaac610e..42914ece99 100644 --- a/app/client/src/utils/storage.ts +++ b/app/client/src/utils/storage.ts @@ -38,6 +38,7 @@ export const STORAGE_KEYS: { AI_KNOWLEDGE_BASE: "AI_KNOWLEDGE_BASE", PARTNER_PROGRAM_CALLOUT: "PARTNER_PROGRAM_CALLOUT", IDE_VIEW_MODE: "IDE_VIEW_MODE", + CODE_WIDGET_NAVIGATION_USED: "CODE_WIDGET_NAVIGATION_USED", }; const store = localforage.createInstance({ @@ -882,3 +883,26 @@ export const retrieveIDEViewMode = async (): Promise< log.error(error); } }; + +export const storeCodeWidgetNavigationUsed = async (count: number) => { + try { + await store.setItem(STORAGE_KEYS.CODE_WIDGET_NAVIGATION_USED, count); + return true; + } catch (error) { + log.error("An error occurred while setting CODE_WIDGET_NAVIGATION_USED"); + log.error(error); + } +}; + +export const retrieveCodeWidgetNavigationUsed = async (): Promise => { + try { + const mode = (await store.getItem( + STORAGE_KEYS.CODE_WIDGET_NAVIGATION_USED, + )) as number; + return mode || 0; + } catch (error) { + log.error("An error occurred while fetching CODE_WIDGET_NAVIGATION_USED"); + log.error(error); + return 0; + } +}; diff --git a/app/client/src/widgets/TableWidgetV2/component/header/actions/filter/FilterPane.tsx b/app/client/src/widgets/TableWidgetV2/component/header/actions/filter/FilterPane.tsx index 4da3d76e0f..c7a4e5f028 100644 --- a/app/client/src/widgets/TableWidgetV2/component/header/actions/filter/FilterPane.tsx +++ b/app/client/src/widgets/TableWidgetV2/component/header/actions/filter/FilterPane.tsx @@ -19,8 +19,6 @@ import { getTableFilterState } from "selectors/tableFilterSelectors"; import { getWidgetMetaProps } from "sagas/selectors"; import { ReduxActionTypes } from "@appsmith/constants/ReduxActionConstants"; import type { WidgetProps } from "widgets/BaseWidget"; -import { selectWidgetInitAction } from "actions/widgetSelectionActions"; -import { SelectionRequestType } from "sagas/WidgetSelectUtils"; import { importSvg } from "design-system-old"; import { CANVAS_ART_BOARD } from "constants/componentClassNameConstants"; @@ -155,14 +153,12 @@ const mapDispatchToProps = (dispatch: any) => { position, }, }); - dispatch(selectWidgetInitAction(SelectionRequestType.One, [widgetId])); }, hideFilterPane: (widgetId: string) => { dispatch({ type: ReduxActionTypes.HIDE_TABLE_FILTER_PANE, payload: { widgetId }, }); - dispatch(selectWidgetInitAction(SelectionRequestType.One, [widgetId])); }, }; }; diff --git a/app/client/yarn.lock b/app/client/yarn.lock index 7e7df06642..c455af185e 100644 --- a/app/client/yarn.lock +++ b/app/client/yarn.lock @@ -13220,8 +13220,8 @@ __metadata: d3-geo: ^3.1.0 dayjs: ^1.10.6 deep-diff: ^1.0.2 - design-system: "npm:@appsmithorg/design-system@2.1.35" - design-system-old: "npm:@appsmithorg/design-system-old@1.1.15" + design-system: "npm:@appsmithorg/design-system@2.1.36" + design-system-old: "npm:@appsmithorg/design-system-old@1.1.16" diff: ^5.0.0 dotenv: ^8.1.0 downloadjs: ^1.4.7 @@ -17210,9 +17210,9 @@ __metadata: languageName: node linkType: hard -"design-system-old@npm:@appsmithorg/design-system-old@1.1.15": - version: 1.1.15 - resolution: "@appsmithorg/design-system-old@npm:1.1.15" +"design-system-old@npm:@appsmithorg/design-system-old@1.1.16": + version: 1.1.16 + resolution: "@appsmithorg/design-system-old@npm:1.1.16" dependencies: emoji-mart: 3.0.1 peerDependencies: @@ -17232,13 +17232,13 @@ __metadata: remixicon-react: ^1.0.0 styled-components: 5.3.6 tinycolor2: ^1.4.2 - checksum: 86cbe4523431e0cbe56ad5fcf9e8125ddb55b913442a418c717e30d1340332fc612549f6d458f5f523e8fa9ee96bb7bc3fc5c312255662701d09262766c23832 + checksum: 8fbfba86e54bdcbbb30b8e8b1902408ba0cb13f4d33d36c794f3bc0e281d0e2db8f716c10c6e0a3118f010db24f97c72606885bff4c320f41f5df9564ab6b214 languageName: node linkType: hard -"design-system@npm:@appsmithorg/design-system@2.1.35": - version: 2.1.35 - resolution: "@appsmithorg/design-system@npm:2.1.35" +"design-system@npm:@appsmithorg/design-system@2.1.36": + version: 2.1.36 + resolution: "@appsmithorg/design-system@npm:2.1.36" dependencies: "@radix-ui/react-dialog": ^1.0.2 "@radix-ui/react-dropdown-menu": ^2.0.4 @@ -17268,7 +17268,7 @@ __metadata: react-dom: ^17.0.2 react-router-dom: ^5.0.0 styled-components: ^5.3.6 - checksum: 06937082709a82d1f994977735999a5601427fae3423fe70bca6f5d7e0aaf487c4e3ade43348d91fd8285b2427046393444b9c097a38904e1d4532d8c6b37632 + checksum: 410db12c576560c6195d5b9ed776f1172c00985966b39d75fbfff119694f2227c94521e5e6d1c3068dd2d49fbac37975c2bc05b1284a09ef434ac7bd551bf84c languageName: node linkType: hard diff --git a/app/server/appsmith-plugins/appsmithAiPlugin/src/main/java/com/external/plugins/AppsmithAiPlugin.java b/app/server/appsmith-plugins/appsmithAiPlugin/src/main/java/com/external/plugins/AppsmithAiPlugin.java index 738784c0fe..2e4829a04d 100644 --- a/app/server/appsmith-plugins/appsmithAiPlugin/src/main/java/com/external/plugins/AppsmithAiPlugin.java +++ b/app/server/appsmith-plugins/appsmithAiPlugin/src/main/java/com/external/plugins/AppsmithAiPlugin.java @@ -87,7 +87,9 @@ public class AppsmithAiPlugin extends BasePlugin { TriggerResultDTO triggerResultDTO = new TriggerResultDTO(); triggerResultDTO.setTrigger(response); return Mono.just(triggerResultDTO); - }); + }) + .onErrorResume( + error -> handleError("An error has occurred while trying to upload files", error)); } else if (LIST_FILES.equals(requestType)) { List fileIds = getFileIds(datasourceConfiguration); if (fileIds.isEmpty()) { @@ -101,27 +103,39 @@ public class AppsmithAiPlugin extends BasePlugin { "NO_FILES_AVAILABLE"))); return Mono.just(triggerResultDTO); } - return aiServerService.getFilesStatus(fileIds, sourceDetails).flatMap(fileStatusDTO -> { - List> response = new ArrayList<>(); - fileStatusDTO.getFiles().forEach(file -> { - Map dropdownOption = new HashMap<>(); - if (!file.isProcessed()) { - dropdownOption.put(LABEL, "(Processing...) " + file.getName()); - } else { - dropdownOption.put(LABEL, file.getName()); - } - dropdownOption.put(VALUE, file.getId()); - dropdownOption.put(DISABLED, !file.isProcessed()); - response.add(dropdownOption); - }); - TriggerResultDTO triggerResultDTO = new TriggerResultDTO(); - triggerResultDTO.setTrigger(response); - return Mono.just(triggerResultDTO); - }); + return aiServerService + .getFilesStatus(fileIds, sourceDetails) + .flatMap(fileStatusDTO -> { + List> response = new ArrayList<>(); + fileStatusDTO.getFiles().forEach(file -> { + Map dropdownOption = new HashMap<>(); + if (!file.isProcessed()) { + dropdownOption.put(LABEL, "(Processing...) " + file.getName()); + } else { + dropdownOption.put(LABEL, file.getName()); + } + dropdownOption.put(VALUE, file.getId()); + dropdownOption.put(DISABLED, !file.isProcessed()); + response.add(dropdownOption); + }); + TriggerResultDTO triggerResultDTO = new TriggerResultDTO(); + triggerResultDTO.setTrigger(response); + return Mono.just(triggerResultDTO); + }) + .onErrorResume(error -> + handleError("An error has occurred while trying to list uploaded files", error)); } return super.trigger(connection, datasourceConfiguration, request); } + private Mono handleError(String message, Throwable error) { + log.error("{}. Error: {}", message, error.getMessage()); + if (!(error instanceof AppsmithPluginException)) { + error = new AppsmithPluginException(AppsmithPluginError.PLUGIN_ERROR, error.getMessage(), error); + } + return Mono.error(error); + } + @Override public Mono executeParameterized( APIConnection connection, diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/base/ActionCollectionServiceCE.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/base/ActionCollectionServiceCE.java index ea02ff2083..61a9de6e9e 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/base/ActionCollectionServiceCE.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/base/ActionCollectionServiceCE.java @@ -82,5 +82,9 @@ public interface ActionCollectionServiceCE extends CrudService generateActionCollectionViewDTO(ActionCollection actionCollection); + Mono bulkValidateAndInsertActionCollectionInRepository(List actionCollectionList); + + Mono bulkValidateAndUpdateActionCollectionInRepository(List actionCollectionList); + Mono saveLastEditInformationInParent(ActionCollectionDTO actionCollectionDTO); } diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/base/ActionCollectionServiceCEImpl.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/base/ActionCollectionServiceCEImpl.java index 7f6fbde919..48542fa1b2 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/base/ActionCollectionServiceCEImpl.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/base/ActionCollectionServiceCEImpl.java @@ -17,7 +17,6 @@ import com.appsmith.server.dtos.ActionCollectionDTO; import com.appsmith.server.dtos.ActionCollectionViewDTO; import com.appsmith.server.exceptions.AppsmithError; import com.appsmith.server.exceptions.AppsmithException; -import com.appsmith.server.helpers.DefaultResourcesUtils; import com.appsmith.server.helpers.ResponseUtils; import com.appsmith.server.newactions.base.NewActionService; import com.appsmith.server.repositories.ActionCollectionRepository; @@ -63,6 +62,9 @@ public class ActionCollectionServiceCEImpl extends BaseService defaultResourcesService; + private final DefaultResourcesService dtoDefaultResourcesService; + private final DefaultResourcesService newActionDefaultResourcesService; + private final DefaultResourcesService actionDTODefaultResourcesService; @Autowired public ActionCollectionServiceCEImpl( @@ -75,7 +77,10 @@ public class ActionCollectionServiceCEImpl extends BaseService defaultResourcesService) { + DefaultResourcesService defaultResourcesService, + DefaultResourcesService dtoDefaultResourcesService, + DefaultResourcesService newActionDefaultResourcesService, + DefaultResourcesService actionDTODefaultResourcesService) { super(validator, repository, analyticsService); this.newActionService = newActionService; @@ -85,6 +90,9 @@ public class ActionCollectionServiceCEImpl extends BaseService generateActionCollectionViewDTO(ActionCollection actionCollection) { + return generateActionCollectionViewDTO(actionCollection, actionPermission.getExecutePermission(), true); + } + + protected Mono generateActionCollectionViewDTO( + ActionCollection actionCollection, AclPermission aclPermission, boolean viewMode) { if (actionCollection.getPublishedCollection() == null) { return Mono.empty(); } @@ -256,8 +269,7 @@ public class ActionCollectionServiceCEImpl extends BaseService newActionService.findActionDTObyIdAndViewMode( - actionId, true, actionPermission.getExecutePermission())) + .flatMap(actionId -> newActionService.findActionDTObyIdAndViewMode(actionId, viewMode, aclPermission)) .collectList() .map(actionDTOList -> { actionCollectionViewDTO.setActions(actionDTOList); @@ -670,6 +682,8 @@ public class ActionCollectionServiceCEImpl extends BaseService sendAnalyticsMono = analyticsService.sendCreateEvent(newAction, newActionService.getAnalyticsProperties(newAction)); @@ -701,20 +719,9 @@ public class ActionCollectionServiceCEImpl extends BaseService validateAndSaveCollection(ActionCollection actionCollection) { ActionCollectionDTO collectionDTO = actionCollection.getUnpublishedCollection(); - final Set validationMessages = collectionDTO.validate(); - if (!validationMessages.isEmpty()) { - return Mono.error(new AppsmithException( - AppsmithError.INVALID_ACTION_COLLECTION, collectionDTO.getName(), validationMessages.toString())); - } - DefaultResources defaultResources = collectionDTO.getDefaultResources(); - - if (defaultResources == null) { - DefaultResourcesUtils.createDefaultIdsOrUpdateWithGivenResourceIds(collectionDTO, null); - actionCollection.setDefaultResources(collectionDTO.getDefaultResources()); - } - - return Mono.justOrEmpty(collectionDTO.getActions()) + return validateActionCollection(actionCollection) + .thenReturn(collectionDTO.getActions()) .defaultIfEmpty(List.of()) .flatMapMany(Flux::fromIterable) .flatMap(action -> { @@ -773,6 +780,45 @@ public class ActionCollectionServiceCEImpl extends BaseService validateActionCollection(ActionCollection actionCollection) { + ActionCollectionDTO collectionDTO = actionCollection.getUnpublishedCollection(); + + collectionDTO.populateTransientFields(actionCollection); + + final Set validationMessages = collectionDTO.validate(); + if (!validationMessages.isEmpty()) { + return Mono.error(new AppsmithException( + AppsmithError.INVALID_ACTION_COLLECTION, collectionDTO.getName(), validationMessages.toString())); + } + + String branchName = null; + + if (actionCollection.getDefaultResources() != null) { + branchName = actionCollection.getDefaultResources().getBranchName(); + } + + defaultResourcesService.initialize(actionCollection, branchName, false); + dtoDefaultResourcesService.initialize(collectionDTO, branchName, false); + + return Mono.just(actionCollection); + } + + @Override + public Mono bulkValidateAndInsertActionCollectionInRepository(List actionCollectionList) { + return Flux.fromIterable(actionCollectionList) + .flatMap(this::validateActionCollection) + .collectList() + .flatMap(repository::bulkInsert); + } + + @Override + public Mono bulkValidateAndUpdateActionCollectionInRepository(List actionCollectionList) { + return Flux.fromIterable(actionCollectionList) + .flatMap(this::validateActionCollection) + .collectList() + .flatMap(repository::bulkUpdate); + } + protected void populateDefaultResources( ActionCollection actionCollection, ActionCollectionDTO collectionDTO, List actions) { // Store the default resource ids diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/base/ActionCollectionServiceImpl.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/base/ActionCollectionServiceImpl.java index d4a2521d12..c0bbe886c3 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/base/ActionCollectionServiceImpl.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/base/ActionCollectionServiceImpl.java @@ -1,9 +1,12 @@ package com.appsmith.server.actioncollections.base; +import com.appsmith.external.models.ActionDTO; import com.appsmith.server.acl.PolicyGenerator; import com.appsmith.server.applications.base.ApplicationService; import com.appsmith.server.defaultresources.DefaultResourcesService; import com.appsmith.server.domains.ActionCollection; +import com.appsmith.server.domains.NewAction; +import com.appsmith.server.dtos.ActionCollectionDTO; import com.appsmith.server.helpers.ResponseUtils; import com.appsmith.server.newactions.base.NewActionService; import com.appsmith.server.repositories.ActionCollectionRepository; @@ -17,7 +20,6 @@ import org.springframework.stereotype.Service; @Service @Slf4j public class ActionCollectionServiceImpl extends ActionCollectionServiceCEImpl implements ActionCollectionService { - public ActionCollectionServiceImpl( Validator validator, ActionCollectionRepository repository, @@ -28,7 +30,10 @@ public class ActionCollectionServiceImpl extends ActionCollectionServiceCEImpl i ResponseUtils responseUtils, ApplicationPermission applicationPermission, ActionPermission actionPermission, - DefaultResourcesService defaultResourcesService) { + DefaultResourcesService defaultResourcesService, + DefaultResourcesService dtoDefaultResourcesService, + DefaultResourcesService newActionDefaultResourcesService, + DefaultResourcesService actionDTODefaultResourcesService) { super( validator, repository, @@ -39,6 +44,9 @@ public class ActionCollectionServiceImpl extends ActionCollectionServiceCEImpl i responseUtils, applicationPermission, actionPermission, - defaultResourcesService); + defaultResourcesService, + dtoDefaultResourcesService, + newActionDefaultResourcesService, + actionDTODefaultResourcesService); } } diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/importable/ActionCollectionImportableServiceCEImpl.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/importable/ActionCollectionImportableServiceCEImpl.java index 953e67c608..9f18888299 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/importable/ActionCollectionImportableServiceCEImpl.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/importable/ActionCollectionImportableServiceCEImpl.java @@ -1,6 +1,7 @@ package com.appsmith.server.actioncollections.importable; import com.appsmith.external.models.Policy; +import com.appsmith.server.actioncollections.base.ActionCollectionService; import com.appsmith.server.domains.ActionCollection; import com.appsmith.server.domains.Application; import com.appsmith.server.domains.Artifact; @@ -33,6 +34,8 @@ import static com.appsmith.external.helpers.AppsmithBeanUtils.copyNestedNonNullP @Service @RequiredArgsConstructor public class ActionCollectionImportableServiceCEImpl implements ImportableServiceCE { + + private final ActionCollectionService actionCollectionService; private final ActionCollectionRepository repository; protected final ArtifactBasedImportableService applicationImportableService; @@ -72,7 +75,7 @@ public class ActionCollectionImportableServiceCEImpl implements ImportableServic ImportingMetaDTO importingMetaDTO, MappedImportableResourcesDTO mappedImportableResourcesDTO) { - ArtifactBasedImportableService artifactBasedExportableService = + ArtifactBasedImportableService artifactBasedImportableService = getArtifactBasedImportableService(importingMetaDTO); Mono> importedActionCollectionMono = Mono.just(importedActionCollectionList); @@ -80,14 +83,14 @@ public class ActionCollectionImportableServiceCEImpl implements ImportableServic if (importingMetaDTO.getAppendToArtifact()) { importedActionCollectionMono = importedActionCollectionMono.map(importedActionCollections -> { List importedContextNames = - artifactBasedExportableService.getImportedContextNames(mappedImportableResourcesDTO); + artifactBasedImportableService.getImportedContextNames(mappedImportableResourcesDTO); Map newToOldNameMap = mappedImportableResourcesDTO.getContextNewNameToOldName(); for (String newContextName : importedContextNames) { String oldContextName = newToOldNameMap.get(newContextName); if (!newContextName.equals(oldContextName)) { - artifactBasedExportableService.renameContextInImportableResources( + artifactBasedImportableService.renameContextInImportableResources( importedActionCollections, oldContextName, newContextName); } } @@ -122,7 +125,7 @@ public class ActionCollectionImportableServiceCEImpl implements ImportableServic ImportingMetaDTO importingMetaDTO, MappedImportableResourcesDTO mappedImportableResourcesDTO) { - ArtifactBasedImportableService artifactBasedExportableService = + ArtifactBasedImportableService artifactBasedImportableService = getArtifactBasedImportableService(importingMetaDTO); /* Mono.just(importableArtifact) is created to avoid the eagerly fetching of existing actionCollections @@ -135,7 +138,7 @@ public class ActionCollectionImportableServiceCEImpl implements ImportableServic // Map of gitSyncId to actionCollection of the existing records in DB Mono> actionCollectionsInCurrentArtifactMono = - artifactBasedExportableService + artifactBasedImportableService .getExistingResourcesInCurrentArtifactFlux(artifact) .filter(collection -> collection.getGitSyncId() != null) .collectMap(ActionCollection::getGitSyncId); @@ -144,7 +147,7 @@ public class ActionCollectionImportableServiceCEImpl implements ImportableServic if (artifact.getGitArtifactMetadata() != null) { final String defaultArtifactId = artifact.getGitArtifactMetadata().getDefaultArtifactId(); - actionCollectionsInBranchesMono = artifactBasedExportableService + actionCollectionsInBranchesMono = artifactBasedImportableService .getExistingResourcesInOtherBranchesFlux(defaultArtifactId, artifact.getId()) .filter(actionCollection -> actionCollection.getGitSyncId() != null) .collectMap(ActionCollection::getGitSyncId); @@ -187,10 +190,11 @@ public class ActionCollectionImportableServiceCEImpl implements ImportableServic if (actionsCollectionsInBranches.containsKey(actionCollection.getGitSyncId())) { branchedActionCollection = - getExistingCollectionInOtherBranchesForImportedCollection( - mappedImportableResourcesDTO, - actionsCollectionsInBranches, - actionCollection); + artifactBasedImportableService + .getExistingEntityInOtherBranchForImportedEntity( + mappedImportableResourcesDTO, + actionsCollectionsInBranches, + actionCollection); } Context defaultContext = populateIdReferencesAndReturnDefaultContext( @@ -206,10 +210,11 @@ public class ActionCollectionImportableServiceCEImpl implements ImportableServic // Since the resource is already present in DB, just update resource ActionCollection existingActionCollection = - getExistingCollectionInCurrentBranchForImportedCollection( - mappedImportableResourcesDTO, - actionsCollectionsInCurrentArtifact, - actionCollection); + artifactBasedImportableService + .getExistingEntityInCurrentBranchForImportedEntity( + mappedImportableResourcesDTO, + actionsCollectionsInCurrentArtifact, + actionCollection); updateExistingCollection( importingMetaDTO, @@ -223,7 +228,7 @@ public class ActionCollectionImportableServiceCEImpl implements ImportableServic .getSavedActionCollectionMap() .put(idFromJsonFile, existingActionCollection); } else { - artifactBasedExportableService.createNewResource( + artifactBasedImportableService.createNewResource( importingMetaDTO, actionCollection, defaultContext); populateDomainMappedReferences(mappedImportableResourcesDTO, actionCollection); @@ -238,9 +243,13 @@ public class ActionCollectionImportableServiceCEImpl implements ImportableServic "Saving action collections in bulk. New: {}, Updated: {}", newActionCollections.size(), existingActionCollections.size()); - return repository - .bulkInsert(newActionCollections) - .then(repository.bulkUpdate(existingActionCollections)) + return Mono.when( + actionCollectionService + .bulkValidateAndInsertActionCollectionInRepository( + newActionCollections), + actionCollectionService + .bulkValidateAndUpdateActionCollectionInRepository( + existingActionCollections)) .thenReturn(resultDTO); }); }) @@ -257,7 +266,7 @@ public class ActionCollectionImportableServiceCEImpl implements ImportableServic ActionCollection branchedActionCollection, ActionCollection actionCollection) { - ArtifactBasedImportableService artifactBasedExportableService = + ArtifactBasedImportableService artifactBasedImportableService = this.getArtifactBasedImportableService(importingMetaDTO); String idFromJsonFile = actionCollection.getId(); @@ -277,7 +286,7 @@ public class ActionCollectionImportableServiceCEImpl implements ImportableServic unpublishedCollection.setPluginId( mappedImportableResourcesDTO.getPluginMap().get(unpublishedCollection.getPluginId())); - parentContext = artifactBasedExportableService.updateContextInResource( + parentContext = artifactBasedImportableService.updateContextInResource( unpublishedCollection, mappedImportableResourcesDTO.getContextMap(), fallbackDefaultContextId); } @@ -289,7 +298,7 @@ public class ActionCollectionImportableServiceCEImpl implements ImportableServic publishedCollection.setPluginId( mappedImportableResourcesDTO.getPluginMap().get(publishedCollection.getPluginId())); - Context publishedCollectionContext = artifactBasedExportableService.updateContextInResource( + Context publishedCollectionContext = artifactBasedImportableService.updateContextInResource( publishedCollection, mappedImportableResourcesDTO.getContextMap(), fallbackDefaultContextId); parentContext = parentContext == null ? publishedCollectionContext : parentContext; } @@ -297,7 +306,7 @@ public class ActionCollectionImportableServiceCEImpl implements ImportableServic actionCollection.makePristine(); actionCollection.setWorkspaceId(workspaceId); - artifactBasedExportableService.populateDefaultResources( + artifactBasedImportableService.populateDefaultResources( importingMetaDTO, mappedImportableResourcesDTO, artifact, branchedActionCollection, actionCollection); return parentContext; } @@ -367,13 +376,6 @@ public class ActionCollectionImportableServiceCEImpl implements ImportableServic return actionsCollectionsInCurrentArtifact.get(actionCollection.getGitSyncId()); } - protected ActionCollection getExistingCollectionInOtherBranchesForImportedCollection( - MappedImportableResourcesDTO mappedImportableResourcesDTO, - Map actionsCollectionsInCurrentArtifact, - ActionCollection actionCollection) { - return actionsCollectionsInCurrentArtifact.get(actionCollection.getGitSyncId()); - } - protected boolean existingArtifactContainsCollection( Map actionsCollectionsInCurrentArtifact, ActionCollection actionCollection) { return actionCollection.getGitSyncId() != null diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/importable/ActionCollectionImportableServiceImpl.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/importable/ActionCollectionImportableServiceImpl.java index 64cd61563b..52cd9c61a9 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/importable/ActionCollectionImportableServiceImpl.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/importable/ActionCollectionImportableServiceImpl.java @@ -1,5 +1,6 @@ package com.appsmith.server.actioncollections.importable; +import com.appsmith.server.actioncollections.base.ActionCollectionService; import com.appsmith.server.domains.ActionCollection; import com.appsmith.server.domains.Application; import com.appsmith.server.imports.importable.ImportableService; @@ -12,8 +13,9 @@ public class ActionCollectionImportableServiceImpl extends ActionCollectionImpor implements ImportableService { public ActionCollectionImportableServiceImpl( + ActionCollectionService actionCollectionService, ActionCollectionRepository repository, ArtifactBasedImportableService applicationImportableService) { - super(repository, applicationImportableService); + super(actionCollectionService, repository, applicationImportableService); } } diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/importable/applications/ActionCollectionApplicationImportableServiceCEImpl.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/importable/applications/ActionCollectionApplicationImportableServiceCEImpl.java index cb98965e33..cf77ea8f7f 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/importable/applications/ActionCollectionApplicationImportableServiceCEImpl.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/actioncollections/importable/applications/ActionCollectionApplicationImportableServiceCEImpl.java @@ -58,7 +58,7 @@ public class ActionCollectionApplicationImportableServiceCEImpl @Override public Flux getExistingResourcesInCurrentArtifactFlux(Artifact artifact) { - return repository.findByApplicationId(artifact.getId()); + return repository.findByApplicationId(artifact.getId(), Optional.empty(), Optional.empty()); } @Override diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/applications/imports/ApplicationImportServiceCEImpl.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/applications/imports/ApplicationImportServiceCEImpl.java index aaf6a38cc1..d8889bd077 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/applications/imports/ApplicationImportServiceCEImpl.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/applications/imports/ApplicationImportServiceCEImpl.java @@ -22,6 +22,7 @@ import com.appsmith.server.dtos.MappedImportableResourcesDTO; import com.appsmith.server.exceptions.AppsmithError; import com.appsmith.server.exceptions.AppsmithException; import com.appsmith.server.helpers.ImportArtifactPermissionProvider; +import com.appsmith.server.helpers.ImportExportUtils; import com.appsmith.server.imports.importable.ImportableService; import com.appsmith.server.imports.internal.artifactbased.ArtifactBasedImportServiceCE; import com.appsmith.server.layouts.UpdateLayoutService; @@ -484,7 +485,19 @@ public class ApplicationImportServiceCEImpl .flatMap(application -> { return Flux.fromIterable(application.getPages()) .map(ApplicationPage::getId) - .flatMap(updateLayoutService::updatePageLayoutsByPageId) + .flatMap(pageId -> { + return updateLayoutService + .updatePageLayoutsByPageId(pageId) + .onErrorResume(throwable -> { + // the error would most probably arise because of update layout error, + // this shouldn't stop the application from getting imported. + String errorMessage = ImportExportUtils.getErrorMessage(throwable); + log.error( + "Error while updating layout. Error: {}", errorMessage, throwable); + // continuing the execution + return Mono.just(""); + }); + }) .collectList() .thenReturn(application); }); diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/configurations/SecurityConfig.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/configurations/SecurityConfig.java index 0c96f2ec11..50c430ccba 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/configurations/SecurityConfig.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/configurations/SecurityConfig.java @@ -9,7 +9,7 @@ import com.appsmith.server.constants.Url; import com.appsmith.server.domains.User; import com.appsmith.server.filters.CSRFFilter; import com.appsmith.server.filters.ConditionalFilter; -import com.appsmith.server.filters.PreAuth; +import com.appsmith.server.filters.LoginRateLimitFilter; import com.appsmith.server.helpers.RedirectHelper; import com.appsmith.server.ratelimiting.RateLimitService; import com.appsmith.server.services.AnalyticsService; @@ -115,12 +115,10 @@ public class SecurityConfig { * hence using RouterFunctions to implement this feature. *

* Future folks: Please check out links: - * - https://www.baeldung.com/spring-webflux-static-content - * - https://docs.spring.io/spring/docs/current/spring-framework-reference/web-reactive.html#webflux-config-static-resources + * - ... + * - ... * - Class ResourceHandlerRegistry * for details. If you figure out a cleaner approach, please modify this function - * - * @return */ @Bean public RouterFunction publicRouter() { @@ -136,8 +134,7 @@ public class SecurityConfig { @Bean public SecurityWebFilterChain internalWebFilterChain(ServerHttpSecurity http) { return http.securityMatcher(new PathPatternParserServerWebExchangeMatcher("/actuator/**")) - .httpBasic() - .authenticationManager(authentication -> { + .httpBasic(httpBasicSpec -> httpBasicSpec.authenticationManager(authentication -> { if (INTERNAL_PASSWORD.equals(authentication.getCredentials().toString())) { return Mono.just(UsernamePasswordAuthenticationToken.authenticated( authentication.getPrincipal(), @@ -147,82 +144,75 @@ public class SecurityConfig { return Mono.just(UsernamePasswordAuthenticationToken.unauthenticated( authentication.getPrincipal(), authentication.getCredentials())); } - }) - .and() - .authorizeExchange() - .anyExchange() - .hasAnyAuthority(INTERNAL) - .and() + })) + .authorizeExchange(authorizeExchangeSpec -> + authorizeExchangeSpec.anyExchange().hasAnyAuthority(INTERNAL)) .build(); } @Bean + @SuppressWarnings("Convert2MethodRef") // Helps readability. public SecurityWebFilterChain securityWebFilterChain(ServerHttpSecurity http) { ServerAuthenticationEntryPointFailureHandler failureHandler = new ServerAuthenticationEntryPointFailureHandler(authenticationEntryPoint); return http // The native CSRF solution doesn't work with WebFlux, yet, but only for WebMVC. So we make our own. - .csrf() - .disable() + .csrf(csrfSpec -> csrfSpec.disable()) .addFilterAt(new CSRFFilter(), SecurityWebFiltersOrder.CSRF) // Default security headers configuration from // https://docs.spring.io/spring-security/site/docs/5.0.x/reference/html/headers.html - .headers() - // Disabled here because add it in NGINX instead. - .contentTypeOptions() - .disable() - // Disabled because we use CSP's `frame-ancestors` instead. - .frameOptions() - .disable() - .and() - .anonymous() - .principal(createAnonymousUser()) - .and() + .headers(headerSpec -> headerSpec + // Disabled here because add it in Caddy instead. + .contentTypeOptions(options -> options.disable()) + // Disabled because we use CSP's `frame-ancestors` instead. + .frameOptions(options -> options.disable())) + .anonymous(anonymousSpec -> anonymousSpec.principal(createAnonymousUser())) // This returns 401 unauthorized for all requests that are not authenticated but authentication is // required // The client will redirect to the login page if we return 401 as Http status response - .exceptionHandling() - .authenticationEntryPoint(authenticationEntryPoint) - .accessDeniedHandler(accessDeniedHandler) - .and() - .authorizeExchange() - .matchers( - ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, Url.LOGIN_URL), - ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, Url.HEALTH_CHECK), - ServerWebExchangeMatchers.pathMatchers(HttpMethod.POST, USER_URL), - ServerWebExchangeMatchers.pathMatchers(HttpMethod.POST, USER_URL + "/super"), - ServerWebExchangeMatchers.pathMatchers(HttpMethod.POST, USER_URL + "/forgotPassword"), - ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, USER_URL + "/verifyPasswordResetToken"), - ServerWebExchangeMatchers.pathMatchers(HttpMethod.PUT, USER_URL + "/resetPassword"), - ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, USER_URL + "/invite/verify"), - ServerWebExchangeMatchers.pathMatchers(HttpMethod.PUT, USER_URL + "/invite/confirm"), - ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, USER_URL + "/me"), - ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, USER_URL + "/features"), - ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, ASSET_URL + "/*"), - ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, ACTION_URL + "/**"), - ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, ACTION_COLLECTION_URL + "/view"), - ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, PAGE_URL + "/**"), - ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, APPLICATION_URL + "/**"), - ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, THEME_URL + "/**"), - ServerWebExchangeMatchers.pathMatchers(HttpMethod.POST, ACTION_URL + "/execute"), - ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, TENANT_URL + "/current"), - ServerWebExchangeMatchers.pathMatchers(HttpMethod.POST, USAGE_PULSE_URL), - ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, CUSTOM_JS_LIB_URL + "/*/view"), - ServerWebExchangeMatchers.pathMatchers(HttpMethod.POST, USER_URL + "/resendEmailVerification"), - ServerWebExchangeMatchers.pathMatchers( - HttpMethod.POST, USER_URL + "/verifyEmailVerificationToken"), - ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, PRODUCT_ALERT + "/alert"), - ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, CONSOLIDATED_API_URL + "/view")) - .permitAll() - .pathMatchers("/public/**", "/oauth2/**") - .permitAll() - .anyExchange() - .authenticated() - .and() + .exceptionHandling(exceptionHandlingSpec -> exceptionHandlingSpec + .authenticationEntryPoint(authenticationEntryPoint) + .accessDeniedHandler(accessDeniedHandler)) + .authorizeExchange(authorizeExchangeSpec -> authorizeExchangeSpec + // The following endpoints are allowed to be accessed without authentication + .matchers( + ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, Url.LOGIN_URL), + ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, Url.HEALTH_CHECK), + ServerWebExchangeMatchers.pathMatchers(HttpMethod.POST, USER_URL), + ServerWebExchangeMatchers.pathMatchers(HttpMethod.POST, USER_URL + "/super"), + ServerWebExchangeMatchers.pathMatchers(HttpMethod.POST, USER_URL + "/forgotPassword"), + ServerWebExchangeMatchers.pathMatchers( + HttpMethod.GET, USER_URL + "/verifyPasswordResetToken"), + ServerWebExchangeMatchers.pathMatchers(HttpMethod.PUT, USER_URL + "/resetPassword"), + ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, USER_URL + "/invite/verify"), + ServerWebExchangeMatchers.pathMatchers(HttpMethod.PUT, USER_URL + "/invite/confirm"), + ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, USER_URL + "/me"), + ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, USER_URL + "/features"), + ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, ASSET_URL + "/*"), + ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, ACTION_URL + "/**"), + ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, ACTION_COLLECTION_URL + "/view"), + ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, PAGE_URL + "/**"), + ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, APPLICATION_URL + "/**"), + ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, THEME_URL + "/**"), + ServerWebExchangeMatchers.pathMatchers(HttpMethod.POST, ACTION_URL + "/execute"), + ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, TENANT_URL + "/current"), + ServerWebExchangeMatchers.pathMatchers(HttpMethod.POST, USAGE_PULSE_URL), + ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, CUSTOM_JS_LIB_URL + "/*/view"), + ServerWebExchangeMatchers.pathMatchers( + HttpMethod.POST, USER_URL + "/resendEmailVerification"), + ServerWebExchangeMatchers.pathMatchers( + HttpMethod.POST, USER_URL + "/verifyEmailVerificationToken"), + ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, PRODUCT_ALERT + "/alert"), + ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, CONSOLIDATED_API_URL + "/view")) + .permitAll() + .pathMatchers("/public/**", "/oauth2/**") + .permitAll() + .anyExchange() + .authenticated()) // Add Pre Auth rate limit filter before authentication filter .addFilterBefore( - new ConditionalFilter(new PreAuth(rateLimitService), Url.LOGIN_URL), + new ConditionalFilter(new LoginRateLimitFilter(rateLimitService), Url.LOGIN_URL), SecurityWebFiltersOrder.FORM_LOGIN) .httpBasic(httpBasicSpec -> httpBasicSpec.authenticationFailureHandler(failureHandler)) .formLogin(formLoginSpec -> formLoginSpec @@ -245,17 +235,14 @@ public class SecurityConfig { .authenticationSuccessHandler(authenticationSuccessHandler) .authenticationFailureHandler(authenticationFailureHandler) .authorizedClientRepository(new ClientUserRepository(userService, commonConfig))) - .logout() - .logoutUrl(Url.LOGOUT_URL) - .logoutSuccessHandler(new LogoutSuccessHandler(objectMapper, analyticsService)) - .and() + .logout(logoutSpec -> logoutSpec + .logoutUrl(Url.LOGOUT_URL) + .logoutSuccessHandler(new LogoutSuccessHandler(objectMapper, analyticsService))) .build(); } /** * This bean configures the parameters that need to be set when a Cookie is created for a logged in user - * - * @return */ @Bean public WebSessionIdResolver webSessionIdResolver() { diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/controllers/ce/ThemeControllerCE.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/controllers/ce/ThemeControllerCE.java index 21505570c5..95c12e8020 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/controllers/ce/ThemeControllerCE.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/controllers/ce/ThemeControllerCE.java @@ -68,16 +68,6 @@ public class ThemeControllerCE extends BaseController new ResponseDTO<>(HttpStatus.OK.value(), theme, null)); } - @JsonView(Views.Public.class) - @PatchMapping("applications/{applicationId}") - public Mono> publishCurrentTheme( - @PathVariable String applicationId, - @RequestBody Theme resource, - @RequestHeader(name = FieldName.BRANCH_NAME, required = false) String branchName) { - return service.persistCurrentTheme(applicationId, branchName, resource) - .map(theme -> new ResponseDTO<>(HttpStatus.OK.value(), theme, null)); - } - @JsonView(Views.Public.class) @PatchMapping("{themeId}") public Mono> updateName(@PathVariable String themeId, @Valid @RequestBody Theme resource) { diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/filters/PreAuth.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/filters/LoginRateLimitFilter.java similarity index 92% rename from app/server/appsmith-server/src/main/java/com/appsmith/server/filters/PreAuth.java rename to app/server/appsmith-server/src/main/java/com/appsmith/server/filters/LoginRateLimitFilter.java index ccaceda3d8..d64ca5d820 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/filters/PreAuth.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/filters/LoginRateLimitFilter.java @@ -18,12 +18,12 @@ import java.nio.charset.StandardCharsets; import static java.lang.Boolean.FALSE; @Slf4j -public class PreAuth implements WebFilter { +public class LoginRateLimitFilter implements WebFilter { private final ServerRedirectStrategy redirectStrategy = new DefaultServerRedirectStrategy(); private final RateLimitService rateLimitService; - public PreAuth(RateLimitService rateLimitService) { + public LoginRateLimitFilter(RateLimitService rateLimitService) { this.rateLimitService = rateLimitService; } @@ -52,7 +52,7 @@ public class PreAuth implements WebFilter { private Mono getUsername(ServerWebExchange exchange) { return exchange.getFormData() - .map(formData -> formData.getFirst(FieldName.USERNAME.toString())) + .mapNotNull(formData -> formData.getFirst(FieldName.USERNAME.toString())) .defaultIfEmpty(""); } diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/helpers/ce/bridge/BridgeQuery.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/helpers/ce/bridge/BridgeQuery.java index 182917e5bd..643c98b003 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/helpers/ce/bridge/BridgeQuery.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/helpers/ce/bridge/BridgeQuery.java @@ -88,13 +88,8 @@ public final class BridgeQuery extends Criteria { return this; } - public BridgeQuery or(BridgeQuery... items) { - checks.add(new Criteria().orOperator(items)); - return this; - } - - public BridgeQuery and(BridgeQuery... items) { - checks.add(new Criteria().andOperator(items)); + public BridgeQuery and(BridgeQuery item) { + checks.add(new Criteria().andOperator(item)); return this; } diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/imports/importable/artifactbased/ArtifactBasedImportableServiceCE.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/imports/importable/artifactbased/ArtifactBasedImportableServiceCE.java index e0aeee6b44..ff8f44ab5b 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/imports/importable/artifactbased/ArtifactBasedImportableServiceCE.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/imports/importable/artifactbased/ArtifactBasedImportableServiceCE.java @@ -30,4 +30,16 @@ public interface ArtifactBasedImportableServiceCE entityInCurrentArtifact, + T entity) { + return entityInCurrentArtifact.get(entity.getGitSyncId()); + } + + default T getExistingEntityInOtherBranchForImportedEntity( + MappedImportableResourcesDTO mappedImportableResourcesDTO, Map entityInOtherArtifact, T entity) { + return entityInOtherArtifact.get(entity.getGitSyncId()); + } } diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/newactions/base/NewActionServiceCE.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/newactions/base/NewActionServiceCE.java index 5c90365906..768a422a41 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/newactions/base/NewActionServiceCE.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/newactions/base/NewActionServiceCE.java @@ -122,7 +122,7 @@ public interface NewActionServiceCE extends CrudService { Flux getUnpublishedActionsExceptJs(MultiValueMap params, String branchName); Mono findByBranchNameAndDefaultActionId( - String branchName, String defaultActionId, AclPermission permission); + String branchName, String defaultActionId, Boolean viewMode, AclPermission permission); Mono findBranchedIdByBranchNameAndDefaultActionId( String branchName, String defaultActionId, AclPermission permission); diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/newactions/base/NewActionServiceCEImpl.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/newactions/base/NewActionServiceCEImpl.java index 82af61e43f..df9ac0dbde 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/newactions/base/NewActionServiceCEImpl.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/newactions/base/NewActionServiceCEImpl.java @@ -212,7 +212,7 @@ public class NewActionServiceCEImpl extends BaseService findByIdAndBranchName(String id, String branchName) { - return this.findByBranchNameAndDefaultActionId(branchName, id, actionPermission.getReadPermission()) + return this.findByBranchNameAndDefaultActionId(branchName, id, false, actionPermission.getReadPermission()) .map(responseUtils::updateNewActionWithDefaultResources); } @@ -1473,7 +1473,7 @@ public class NewActionServiceCEImpl extends BaseService archiveByIdAndBranchName(String id, String branchName) { Mono branchedActionMono = - this.findByBranchNameAndDefaultActionId(branchName, id, actionPermission.getDeletePermission()); + this.findByBranchNameAndDefaultActionId(branchName, id, false, actionPermission.getDeletePermission()); return branchedActionMono .flatMap(branchedAction -> this.archiveById(branchedAction.getId())) @@ -1560,7 +1560,7 @@ public class NewActionServiceCEImpl extends BaseService findByBranchNameAndDefaultActionId( - String branchName, String defaultActionId, AclPermission permission) { + String branchName, String defaultActionId, Boolean viewMode, AclPermission permission) { log.debug("Going to find action based on branchName and defaultActionId with id: {} ", defaultActionId); if (!StringUtils.hasLength(branchName)) { return repository @@ -1569,7 +1569,7 @@ public class NewActionServiceCEImpl extends BaseService artifactBasedExportableService = + ArtifactBasedImportableService artifactBasedImportableService = getArtifactBasedImportableService(importingMetaDTO); Mono> importedNewActionMono = Mono.justOrEmpty(importedNewActions); @@ -210,14 +210,14 @@ public class NewActionImportableServiceCEImpl implements ImportableServiceCE { List importedContextNames = - artifactBasedExportableService.getImportedContextNames(mappedImportableResourcesDTO); + artifactBasedImportableService.getImportedContextNames(mappedImportableResourcesDTO); Map newToOldNameMap = mappedImportableResourcesDTO.getContextNewNameToOldName(); for (String newContextName : importedContextNames) { String oldContextName = newToOldNameMap.get(newContextName); if (!newContextName.equals(oldContextName)) { - artifactBasedExportableService.renameContextInImportableResources( + artifactBasedImportableService.renameContextInImportableResources( importedNewActionList, oldContextName, newContextName); } } @@ -248,7 +248,7 @@ public class NewActionImportableServiceCEImpl implements ImportableServiceCE artifactBasedExportableService = + ArtifactBasedImportableService artifactBasedImportableService = getArtifactBasedImportableService(importingMetaDTO); /* Mono.just(importableArtifact) is created to avoid the eagerly fetching of existing actions @@ -258,7 +258,7 @@ public class NewActionImportableServiceCEImpl implements ImportableServiceCE> actionsInCurrentArtifactMono = artifactBasedExportableService + Mono> actionsInCurrentArtifactMono = artifactBasedImportableService .getExistingResourcesInCurrentArtifactFlux(artifact) .filter(collection -> collection.getGitSyncId() != null) .collectMap(NewAction::getGitSyncId); @@ -268,7 +268,7 @@ public class NewActionImportableServiceCEImpl implements ImportableServiceCE newAction.getGitSyncId() != null) .collectMap(NewAction::getGitSyncId); @@ -305,8 +305,9 @@ public class NewActionImportableServiceCEImpl implements ImportableServiceCE actionsInCurrentArtifact, - NewAction newAction) { - return actionsInCurrentArtifact.get(newAction.getGitSyncId()); - } - protected boolean existingArtifactContainsAction( Map actionsInCurrentArtifact, NewAction newAction) { return newAction.getGitSyncId() != null && actionsInCurrentArtifact.containsKey(newAction.getGitSyncId()); diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/newactions/importable/applications/NewActionApplicationImportableServiceCEImpl.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/newactions/importable/applications/NewActionApplicationImportableServiceCEImpl.java index 071914873a..030ab4ab56 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/newactions/importable/applications/NewActionApplicationImportableServiceCEImpl.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/newactions/importable/applications/NewActionApplicationImportableServiceCEImpl.java @@ -58,7 +58,7 @@ public class NewActionApplicationImportableServiceCEImpl @Override public Flux getExistingResourcesInCurrentArtifactFlux(Artifact artifact) { - return repository.findByApplicationId(artifact.getId()); + return repository.findByApplicationId(artifact.getId(), Optional.empty(), Optional.empty()); } @Override diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/newactions/refactors/JsActionRefactoringServiceCEImpl.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/newactions/refactors/JsActionRefactoringServiceCEImpl.java index 2d6f530eda..54141556a9 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/newactions/refactors/JsActionRefactoringServiceCEImpl.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/newactions/refactors/JsActionRefactoringServiceCEImpl.java @@ -56,7 +56,7 @@ public class JsActionRefactoringServiceCEImpl implements EntityRefactoringServic // Fetch branched action as client only knows about the default action IDs Mono branchedActionMono = newActionService .findByBranchNameAndDefaultActionId( - branchName, refactorEntityNameDTO.getActionId(), actionPermission.getEditPermission()) + branchName, refactorEntityNameDTO.getActionId(), false, actionPermission.getEditPermission()) .map(branchedAction -> { refactorEntityNameDTO.setActionId(branchedAction.getId()); defaultActionCollection.setPageId( diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/newactions/refactors/NewActionRefactoringServiceCEImpl.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/newactions/refactors/NewActionRefactoringServiceCEImpl.java index 61769ba9bb..71d7f245a1 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/newactions/refactors/NewActionRefactoringServiceCEImpl.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/newactions/refactors/NewActionRefactoringServiceCEImpl.java @@ -127,7 +127,7 @@ public class NewActionRefactoringServiceCEImpl implements EntityRefactoringServi public Mono updateRefactoredEntity(RefactorEntityNameDTO refactorEntityNameDTO, String branchName) { return newActionService .findByBranchNameAndDefaultActionId( - branchName, refactorEntityNameDTO.getActionId(), actionPermission.getEditPermission()) + branchName, refactorEntityNameDTO.getActionId(), false, actionPermission.getEditPermission()) .map(branchedAction -> newActionService.generateActionByViewMode(branchedAction, false)) .flatMap(action -> { action.setName(refactorEntityNameDTO.getNewName()); diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/BaseAppsmithRepositoryCEImpl.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/BaseAppsmithRepositoryCEImpl.java index 3eda9b1f9c..86360a1b1d 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/BaseAppsmithRepositoryCEImpl.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/BaseAppsmithRepositoryCEImpl.java @@ -131,6 +131,11 @@ public abstract class BaseAppsmithRepositoryCEImpl { .is(permission.getValue())); } + /** + * @deprecated Consider using {@code queryBuilder().byId(id)} or {@code Bridge.equal(BaseDomain.Fields.id, id)} + * instead. + */ + @Deprecated(forRemoval = true) protected Criteria getIdCriteria(Object id) { return where("id").is(id); } diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/CustomActionCollectionRepositoryCEImpl.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/CustomActionCollectionRepositoryCEImpl.java index f20a19ac73..8a32e9e174 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/CustomActionCollectionRepositoryCEImpl.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/CustomActionCollectionRepositoryCEImpl.java @@ -51,11 +51,17 @@ public class CustomActionCollectionRepositoryCEImpl extends BaseAppsmithReposito public Flux findByApplicationId( String applicationId, Optional aclPermission, Optional sort) { - Criteria applicationCriteria = - where(ActionCollection.Fields.applicationId).is(applicationId); + List criteria = new ArrayList<>(); + + Criteria applicationCriteria = Criteria.where(FieldName.APPLICATION_ID).is(applicationId); + criteria.add(applicationCriteria); + + Criteria deletedCriteria = + where(ActionCollection.Fields.unpublishedCollection_deletedAt).is(null); + criteria.add(deletedCriteria); return queryBuilder() - .criteria(applicationCriteria) + .criteria(criteria) .permission(aclPermission.orElse(null)) .sort(sort.orElse(null)) .all(); @@ -219,11 +225,19 @@ public class CustomActionCollectionRepositoryCEImpl extends BaseAppsmithReposito @Override public Flux findByDefaultApplicationId( String defaultApplicationId, Optional permission) { + List criteria = new ArrayList<>(); + final String defaultResources = BranchAwareDomain.Fields.defaultResources; Criteria defaultAppIdCriteria = where(defaultResources + "." + FieldName.APPLICATION_ID).is(defaultApplicationId); + criteria.add(defaultAppIdCriteria); + + Criteria deletedCriteria = + where(ActionCollection.Fields.unpublishedCollection_deletedAt).is(null); + criteria.add(deletedCriteria); + return queryBuilder() - .criteria(defaultAppIdCriteria) + .criteria(criteria) .permission(permission.orElse(null)) .all(); } @@ -247,7 +261,9 @@ public class CustomActionCollectionRepositoryCEImpl extends BaseAppsmithReposito @Override public Flux findAllByApplicationIds(List applicationIds, List includeFields) { + Criteria applicationCriteria = Criteria.where(FieldName.APPLICATION_ID).in(applicationIds); + return queryBuilder() .criteria(applicationCriteria) .fields(includeFields) diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/CustomApplicationRepositoryCEImpl.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/CustomApplicationRepositoryCEImpl.java index ae5d19326f..f2cda6e8f1 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/CustomApplicationRepositoryCEImpl.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/CustomApplicationRepositoryCEImpl.java @@ -1,11 +1,11 @@ package com.appsmith.server.repositories.ce; -import com.appsmith.external.models.BaseDomain; import com.appsmith.server.acl.AclPermission; import com.appsmith.server.domains.Application; import com.appsmith.server.domains.ApplicationPage; import com.appsmith.server.domains.User; import com.appsmith.server.helpers.ce.bridge.Bridge; +import com.appsmith.server.helpers.ce.bridge.BridgeQuery; import com.appsmith.server.repositories.BaseAppsmithRepositoryImpl; import com.appsmith.server.repositories.CacheableRepositoryHelper; import com.appsmith.server.solutions.ApplicationPermission; @@ -15,7 +15,6 @@ import org.bson.types.ObjectId; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.data.mongodb.core.ReactiveMongoOperations; import org.springframework.data.mongodb.core.convert.MongoConverter; -import org.springframework.data.mongodb.core.query.Criteria; import org.springframework.data.mongodb.core.query.Update; import org.springframework.security.core.context.ReactiveSecurityContextHolder; import org.springframework.util.StringUtils; @@ -26,8 +25,6 @@ import java.util.List; import java.util.Optional; import java.util.Set; -import static org.springframework.data.mongodb.core.query.Criteria.where; - @Slf4j public class CustomApplicationRepositoryCEImpl extends BaseAppsmithRepositoryImpl implements CustomApplicationRepositoryCE { @@ -46,11 +43,6 @@ public class CustomApplicationRepositoryCEImpl extends BaseAppsmithRepositoryImp this.applicationPermission = applicationPermission; } - @Override - protected Criteria getIdCriteria(Object id) { - return where(Application.Fields.id).is(id); - } - @Override public Mono findByIdAndWorkspaceId(String id, String workspaceId, AclPermission permission) { return queryBuilder() @@ -78,9 +70,8 @@ public class CustomApplicationRepositoryCEImpl extends BaseAppsmithRepositoryImp @Override public Flux findByMultipleWorkspaceIds(Set workspaceIds, AclPermission permission) { - Criteria workspaceIdCriteria = where(Application.Fields.workspaceId).in(workspaceIds); return queryBuilder() - .criteria(workspaceIdCriteria) + .criteria(Bridge.in(Application.Fields.workspaceId, workspaceIds)) .permission(permission) .all(); } @@ -249,18 +240,11 @@ public class CustomApplicationRepositoryCEImpl extends BaseAppsmithRepositoryImp @Override public Flux getAllApplicationIdsInWorkspaceAccessibleToARoleWithPermission( String workspaceId, AclPermission permission, String permissionGroupId) { - Criteria workspaceIdCriteria = - Criteria.where(Application.Fields.workspaceId).is(workspaceId); - - // Check if the permission is being provided by the given permission group - Criteria permissionGroupCriteria = Criteria.where(BaseDomain.Fields.policies) - .elemMatch(Criteria.where("permissionGroups") - .in(permissionGroupId) - .and("permission") - .is(permission.getValue())); - return queryBuilder() - .criteria(workspaceIdCriteria, permissionGroupCriteria) + .criteria(Bridge.equal(Application.Fields.workspaceId, workspaceId)) + // Check if the permission is being provided by the given permission group + .permission(permission) + .permissionGroups(Set.of(permissionGroupId)) .fields(Application.Fields.id) .all() .map(application -> application.getId()); @@ -269,14 +253,10 @@ public class CustomApplicationRepositoryCEImpl extends BaseAppsmithRepositoryImp @Override public Mono getAllApplicationsCountAccessibleToARoleWithPermission( AclPermission permission, String permissionGroupId) { - - Criteria permissionGroupCriteria = Criteria.where(BaseDomain.Fields.policies) - .elemMatch(Criteria.where("permissionGroups") - .in(permissionGroupId) - .and("permission") - .is(permission.getValue())); - - return queryBuilder().criteria(permissionGroupCriteria).count(); + return queryBuilder() + .permission(permission) + .permissionGroups(Set.of(permissionGroupId)) + .count(); } @Override @@ -301,19 +281,12 @@ public class CustomApplicationRepositoryCEImpl extends BaseAppsmithRepositoryImp @Override public Mono protectBranchedApplications( String applicationId, List branchNames, AclPermission permission) { - String isProtectedFieldPath = Application.Fields.gitApplicationMetadata_isProtectedBranch; + final BridgeQuery q = Bridge.equal( + Application.Fields.gitApplicationMetadata_defaultApplicationId, applicationId) + .in(Application.Fields.gitApplicationMetadata_branchName, branchNames); - String branchNameFieldPath = Application.Fields.gitApplicationMetadata_branchName; + Update setProtected = new Update().set(Application.Fields.gitApplicationMetadata_isProtectedBranch, true); - Criteria defaultApplicationIdCriteria = Criteria.where( - Application.Fields.gitApplicationMetadata_defaultApplicationId) - .is(applicationId); - Criteria branchMatchCriteria = Criteria.where(branchNameFieldPath).in(branchNames); - Update setProtected = new Update().set(isProtectedFieldPath, true); - - return queryBuilder() - .criteria(defaultApplicationIdCriteria, branchMatchCriteria) - .permission(permission) - .updateAll(setProtected); + return queryBuilder().criteria(q).permission(permission).updateAll(setProtected); } } diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/CustomNewActionRepositoryCE.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/CustomNewActionRepositoryCE.java index 33965df367..b111d8b0e4 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/CustomNewActionRepositoryCE.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/CustomNewActionRepositoryCE.java @@ -45,7 +45,7 @@ public interface CustomNewActionRepositoryCE extends AppsmithRepository countByDatasourceId(String datasourceId); Mono findByBranchNameAndDefaultActionId( - String branchName, String defaultActionId, AclPermission permission); + String branchName, String defaultActionId, Boolean viewMode, AclPermission permission); Flux findByDefaultApplicationId(String defaultApplicationId, Optional permission); diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/CustomNewActionRepositoryCEImpl.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/CustomNewActionRepositoryCEImpl.java index 47f444cbff..0fc034da77 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/CustomNewActionRepositoryCEImpl.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/CustomNewActionRepositoryCEImpl.java @@ -61,7 +61,8 @@ public class CustomNewActionRepositoryCEImpl extends BaseAppsmithRepositoryImpl< public Flux findByApplicationId( String applicationId, Optional aclPermission, Optional sort) { return queryBuilder() - .criteria(getCriterionForFindByApplicationId(applicationId)) + .criteria(getCriterionForFindByApplicationId(applicationId) + .isNull(NewAction.Fields.unpublishedAction_deletedAt)) .permission(aclPermission.orElse(null)) .sort(sort.orElse(null)) .all(); @@ -167,9 +168,9 @@ public class CustomNewActionRepositoryCEImpl extends BaseAppsmithRepositoryImpl< BridgeQuery q = Bridge.equal(NewAction.Fields.unpublishedAction_pageId, pageId); if (names != null) { - q.or( + q.and(Bridge.or( Bridge.in(NewAction.Fields.unpublishedAction_name, names), - Bridge.in(NewAction.Fields.unpublishedAction_fullyQualifiedName, names)); + Bridge.in(NewAction.Fields.unpublishedAction_fullyQualifiedName, names))); } // In case an action has been deleted in edit mode, but still exists in deployed mode, NewAction object would @@ -238,11 +239,18 @@ public class CustomNewActionRepositoryCEImpl extends BaseAppsmithRepositoryImpl< @Override public Mono findByBranchNameAndDefaultActionId( - String branchName, String defaultActionId, AclPermission permission) { + String branchName, String defaultActionId, Boolean viewMode, AclPermission permission) { final String defaultResources = NewAction.Fields.defaultResources; final BridgeQuery q = Bridge.equal( defaultResources + "." + FieldName.ACTION_ID, defaultActionId) .equal(defaultResources + "." + FieldName.BRANCH_NAME, branchName); + + if (Boolean.FALSE.equals(viewMode)) { + // In case an action has been deleted in edit mode, but still exists in deployed mode, NewAction object + // would exist. To handle this, only fetch non-deleted actions + q.isNull(NewAction.Fields.unpublishedAction_deletedAt); + } + return queryBuilder().criteria(q).permission(permission).one(); } @@ -332,7 +340,8 @@ public class CustomNewActionRepositoryCEImpl extends BaseAppsmithRepositoryImpl< public Flux findByDefaultApplicationId(String defaultApplicationId, Optional permission) { final String defaultResources = BranchAwareDomain.Fields.defaultResources; return queryBuilder() - .criteria(Bridge.equal(defaultResources + "." + FieldName.APPLICATION_ID, defaultApplicationId)) + .criteria(Bridge.equal(defaultResources + "." + FieldName.APPLICATION_ID, defaultApplicationId) + .isNull(NewAction.Fields.unpublishedAction_deletedAt)) .permission(permission.orElse(null)) .all(); } diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/CustomNewPageRepositoryCEImpl.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/CustomNewPageRepositoryCEImpl.java index dbd43248ca..ea028ac40d 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/CustomNewPageRepositoryCEImpl.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/repositories/ce/CustomNewPageRepositoryCEImpl.java @@ -3,8 +3,11 @@ package com.appsmith.server.repositories.ce; import com.appsmith.external.models.BranchAwareDomain; import com.appsmith.server.acl.AclPermission; import com.appsmith.server.constants.FieldName; +import com.appsmith.server.domains.Layout; import com.appsmith.server.domains.NewPage; import com.appsmith.server.dtos.PageDTO; +import com.appsmith.server.helpers.ce.bridge.Bridge; +import com.appsmith.server.helpers.ce.bridge.BridgeQuery; import com.appsmith.server.repositories.BaseAppsmithRepositoryImpl; import com.appsmith.server.repositories.CacheableRepositoryHelper; import lombok.extern.slf4j.Slf4j; @@ -19,7 +22,6 @@ import reactor.core.publisher.Flux; import reactor.core.publisher.Mono; import reactor.core.scheduler.Schedulers; -import java.util.ArrayList; import java.util.Collection; import java.util.List; import java.util.Optional; @@ -44,44 +46,35 @@ public class CustomNewPageRepositoryCEImpl extends BaseAppsmithRepositoryImpl findByApplicationId(String applicationId, AclPermission aclPermission) { - Criteria applicationIdCriteria = where(NewPage.Fields.applicationId).is(applicationId); return queryBuilder() - .criteria(applicationIdCriteria) + .criteria(Bridge.equal(NewPage.Fields.applicationId, applicationId)) .permission(aclPermission) .all(); } @Override public Flux findByApplicationId(String applicationId, Optional permission) { - Criteria applicationIdCriteria = where(NewPage.Fields.applicationId).is(applicationId); return queryBuilder() - .criteria(applicationIdCriteria) + .criteria(Bridge.equal(NewPage.Fields.applicationId, applicationId)) .permission(permission.orElse(null)) .all(); } @Override public Flux findByApplicationIdAndNonDeletedEditMode(String applicationId, AclPermission aclPermission) { - Criteria applicationIdCriteria = where(NewPage.Fields.applicationId).is(applicationId); - // In case a page has been deleted in edit mode, but still exists in deployed mode, NewPage object would exist. - // To handle this, only fetch non-deleted pages - Criteria activeEditModeCriteria = - where(NewPage.Fields.unpublishedPage_deletedAt).is(null); - return queryBuilder() - .criteria(applicationIdCriteria, activeEditModeCriteria) - .permission(aclPermission) - .all(); + BridgeQuery q = Bridge.equal(NewPage.Fields.applicationId, applicationId) + // In case a page has been deleted in edit mode, but still exists in deployed mode, NewPage object would + // exist. To handle this, only fetch non-deleted pages + .isNull(NewPage.Fields.unpublishedPage_deletedAt); + return queryBuilder().criteria(q).permission(aclPermission).all(); } @Override public Mono findByIdAndLayoutsIdAndViewMode( String id, String layoutId, AclPermission aclPermission, Boolean viewMode) { - String layoutsIdKey; - String layoutsKey; + final String layoutsKey; - List criteria = new ArrayList<>(); - Criteria idCriterion = getIdCriteria(id); - criteria.add(idCriterion); + final BridgeQuery q = Bridge.equal(NewPage.Fields.id, id); if (Boolean.TRUE.equals(viewMode)) { layoutsKey = NewPage.Fields.publishedPage_layouts; @@ -90,58 +83,39 @@ public class CustomNewPageRepositoryCEImpl extends BaseAppsmithRepositoryImpl findByNameAndViewMode(String name, AclPermission aclPermission, Boolean viewMode) { - - List criteria = new ArrayList<>(); - - Criteria nameCriterion = getNameCriterion(name, viewMode); - criteria.add(nameCriterion); + final BridgeQuery q = getNameCriterion(name, viewMode); if (Boolean.FALSE.equals(viewMode)) { // In case a page has been deleted in edit mode, but still exists in deployed mode, NewPage object would // exist. To handle this, only fetch non-deleted pages - Criteria deletedCriterion = - where(NewPage.Fields.unpublishedPage_deletedAt).is(null); - criteria.add(deletedCriterion); + q.isNull(NewPage.Fields.unpublishedPage_deletedAt); } - return queryBuilder().criteria(criteria).permission(aclPermission).one(); + return queryBuilder().criteria(q).permission(aclPermission).one(); } @Override public Mono findByNameAndApplicationIdAndViewMode( String name, String applicationId, AclPermission aclPermission, Boolean viewMode) { - - List criteria = new ArrayList<>(); - - Criteria nameCriterion = getNameCriterion(name, viewMode); - criteria.add(nameCriterion); - - Criteria applicationIdCriterion = where(NewPage.Fields.applicationId).is(applicationId); - criteria.add(applicationIdCriterion); + BridgeQuery q = getNameCriterion(name, viewMode).equal(NewPage.Fields.applicationId, applicationId); if (Boolean.FALSE.equals(viewMode)) { // In case a page has been deleted in edit mode, but still exists in deployed mode, NewPage object would // exist. To handle this, only fetch non-deleted pages - Criteria deletedCriteria = - where(NewPage.Fields.unpublishedPage_deletedAt).is(null); - criteria.add(deletedCriteria); + q.isNull(NewPage.Fields.unpublishedPage_deletedAt); } - return queryBuilder().criteria(criteria).permission(aclPermission).one(); + return queryBuilder().criteria(q).permission(aclPermission).one(); } @Override @@ -161,24 +135,17 @@ public class CustomNewPageRepositoryCEImpl extends BaseAppsmithRepositoryImpl getNameCriterion(String name, Boolean viewMode) { + return Bridge.equal( + Boolean.TRUE.equals(viewMode) ? NewPage.Fields.publishedPage_name : NewPage.Fields.unpublishedPage_name, + name); } @Override @@ -197,22 +164,18 @@ public class CustomNewPageRepositoryCEImpl extends BaseAppsmithRepositoryImpl findPageByBranchNameAndDefaultPageId( String branchName, String defaultPageId, AclPermission permission) { final String defaultResources = NewPage.Fields.defaultResources; - Criteria defaultPageIdCriteria = - where(defaultResources + "." + FieldName.PAGE_ID).is(defaultPageId); - Criteria branchCriteria = - where(defaultResources + "." + FieldName.BRANCH_NAME).is(branchName); - return queryBuilder() - .criteria(defaultPageIdCriteria, branchCriteria) - .permission(permission) - .one(); + final BridgeQuery q = + // defaultPageIdCriteria + Bridge.equal(defaultResources + "." + FieldName.PAGE_ID, defaultPageId) + // branchCriteria + .equal(defaultResources + "." + FieldName.BRANCH_NAME, branchName); + return queryBuilder().criteria(q).permission(permission).one(); } @Override public Flux findSlugsByApplicationIds(List applicationIds, AclPermission aclPermission) { - Criteria applicationIdCriteria = where(NewPage.Fields.applicationId).in(applicationIds); - return queryBuilder() - .criteria(applicationIdCriteria) + .criteria(Bridge.in(NewPage.Fields.applicationId, applicationIds)) .fields( NewPage.Fields.unpublishedPage_slug, NewPage.Fields.unpublishedPage_customSlug, @@ -233,13 +196,19 @@ public class CustomNewPageRepositoryCEImpl extends BaseAppsmithRepositoryImpl findByGitSyncIdAndDefaultApplicationId( String defaultApplicationId, String gitSyncId, Optional permission) { final String defaultResources = BranchAwareDomain.Fields.defaultResources; - Criteria defaultAppIdCriteria = - where(defaultResources + "." + FieldName.APPLICATION_ID).is(defaultApplicationId); - Criteria gitSyncIdCriteria = where(FieldName.GIT_SYNC_ID).is(gitSyncId); - return queryBuilder() - .criteria(defaultAppIdCriteria, gitSyncIdCriteria) - .permission(permission.orElse(null)) - .first(); + + // defaultAppIdCriteria + final BridgeQuery q = + Bridge.equal(defaultResources + "." + NewPage.Fields.applicationId, defaultApplicationId); + + if (gitSyncId != null) { + // gitSyncIdCriteria + q.equal(NewPage.Fields.gitSyncId, gitSyncId); + } else { + q.isNull(NewPage.Fields.gitSyncId); + } + + return queryBuilder().criteria(q).permission(permission.orElse(null)).first(); } @Override @@ -277,9 +246,8 @@ public class CustomNewPageRepositoryCEImpl extends BaseAppsmithRepositoryImpl findAllByApplicationIdsWithoutPermission( List applicationIds, List includeFields) { - Criteria applicationCriteria = Criteria.where(FieldName.APPLICATION_ID).in(applicationIds); return queryBuilder() - .criteria(applicationCriteria) + .criteria(Bridge.in(FieldName.APPLICATION_ID, applicationIds)) .fields(includeFields) .all(); } diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/services/ce/LayoutActionServiceCEImpl.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/services/ce/LayoutActionServiceCEImpl.java index 5adf5548b1..76edaec336 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/services/ce/LayoutActionServiceCEImpl.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/services/ce/LayoutActionServiceCEImpl.java @@ -211,7 +211,7 @@ public class LayoutActionServiceCEImpl implements LayoutActionServiceCE { .map(NewPage::getId); Mono branchedActionMono = newActionService.findByBranchNameAndDefaultActionId( - branchName, actionMoveDTO.getAction().getId(), actionPermission.getEditPermission()); + branchName, actionMoveDTO.getAction().getId(), false, actionPermission.getEditPermission()); return Mono.zip(toPageMono, branchedActionMono) .flatMap(tuple -> { @@ -253,7 +253,8 @@ public class LayoutActionServiceCEImpl implements LayoutActionServiceCE { public Mono updateSingleActionWithBranchName( String defaultActionId, ActionDTO action, String branchName) { return newActionService - .findByBranchNameAndDefaultActionId(branchName, defaultActionId, actionPermission.getEditPermission()) + .findByBranchNameAndDefaultActionId( + branchName, defaultActionId, false, actionPermission.getEditPermission()) .flatMap(newAction -> updateActionBasedOnContextType(newAction, action)); } @@ -308,7 +309,8 @@ public class LayoutActionServiceCEImpl implements LayoutActionServiceCE { @Override public Mono setExecuteOnLoad(String defaultActionId, String branchName, Boolean isExecuteOnLoad) { return newActionService - .findByBranchNameAndDefaultActionId(branchName, defaultActionId, actionPermission.getEditPermission()) + .findByBranchNameAndDefaultActionId( + branchName, defaultActionId, false, actionPermission.getEditPermission()) .flatMap(branchedAction -> setExecuteOnLoad(branchedAction.getId(), isExecuteOnLoad)) .map(responseUtils::updateActionDTOWithDefaultResources); } @@ -330,7 +332,8 @@ public class LayoutActionServiceCEImpl implements LayoutActionServiceCE { public Mono deleteUnpublishedAction(String defaultActionId, String branchName) { return newActionService - .findByBranchNameAndDefaultActionId(branchName, defaultActionId, actionPermission.getDeletePermission()) + .findByBranchNameAndDefaultActionId( + branchName, defaultActionId, false, actionPermission.getDeletePermission()) .flatMap(branchedAction -> deleteUnpublishedAction(branchedAction.getId())) .map(responseUtils::updateActionDTOWithDefaultResources) .flatMap(actionDTO -> newActionService diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/services/ce/LayoutCollectionServiceCEImpl.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/services/ce/LayoutCollectionServiceCEImpl.java index 7b41ca62f2..8e35bf332f 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/services/ce/LayoutCollectionServiceCEImpl.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/services/ce/LayoutCollectionServiceCEImpl.java @@ -382,6 +382,7 @@ public class LayoutCollectionServiceCEImpl implements LayoutCollectionServiceCE .findByBranchNameAndDefaultActionId( branchName, actionDTO.getId(), + false, actionPermission.getEditPermission()) .map(NewAction::getId); actionDTO.setId(null); @@ -432,6 +433,7 @@ public class LayoutCollectionServiceCEImpl implements LayoutCollectionServiceCE .findByBranchNameAndDefaultActionId( branchName, actionDTO.getId(), + false, actionPermission.getEditPermission()) .map(NewAction::getId); actionDTO.setId(null); diff --git a/app/server/appsmith-server/src/main/java/com/appsmith/server/solutions/ce/ActionExecutionSolutionCEImpl.java b/app/server/appsmith-server/src/main/java/com/appsmith/server/solutions/ce/ActionExecutionSolutionCEImpl.java index 069b1c13ba..8ff75a901b 100644 --- a/app/server/appsmith-server/src/main/java/com/appsmith/server/solutions/ce/ActionExecutionSolutionCEImpl.java +++ b/app/server/appsmith-server/src/main/java/com/appsmith/server/solutions/ce/ActionExecutionSolutionCEImpl.java @@ -190,7 +190,10 @@ public class ActionExecutionSolutionCEImpl implements ActionExecutionSolutionCE AclPermission executePermission = getPermission(executeActionMetaDTO, actionPermission.getExecutePermission()); Mono newActionMono = newActionService .findByBranchNameAndDefaultActionId( - executeActionMetaDTO.getBranchName(), executeActionDTO.getActionId(), executePermission) + executeActionMetaDTO.getBranchName(), + executeActionDTO.getActionId(), + executeActionDTO.getViewMode(), + executePermission) .cache(); Mono populatedExecuteActionDTOMono = @@ -810,11 +813,13 @@ public class ActionExecutionSolutionCEImpl implements ActionExecutionSolutionCE Integer timeoutDuration = actionDTO.getActionConfiguration().getTimeoutInMillisecond(); - setAutoGeneratedHeaders(plugin, actionDTO, httpHeaders); + Mono actionDTOWithAutoGeneratedHeadersMono = + setAutoGeneratedHeaders(plugin, actionDTO, httpHeaders); - Mono actionExecutionResultMono = verifyDatasourceAndMakeRequest( - executeActionDTO, actionDTO, datasourceStorage, plugin, pluginExecutor) - .timeout(Duration.ofMillis(timeoutDuration)); + Mono actionExecutionResultMono = + actionDTOWithAutoGeneratedHeadersMono.flatMap(actionDTO1 -> verifyDatasourceAndMakeRequest( + executeActionDTO, actionDTO, datasourceStorage, plugin, pluginExecutor) + .timeout(Duration.ofMillis(timeoutDuration))); return actionExecutionResultMono .onErrorMap(executionExceptionMapper(actionDTO, timeoutDuration)) @@ -1136,5 +1141,7 @@ public class ActionExecutionSolutionCEImpl implements ActionExecutionSolutionCE }); } - protected void setAutoGeneratedHeaders(Plugin plugin, ActionDTO actionDTO, HttpHeaders httpHeaders) {} + protected Mono setAutoGeneratedHeaders(Plugin plugin, ActionDTO actionDTO, HttpHeaders httpHeaders) { + return Mono.just(actionDTO); + } } diff --git a/app/server/appsmith-server/src/test/java/com/appsmith/server/imports/internal/ImportServiceTests.java b/app/server/appsmith-server/src/test/java/com/appsmith/server/imports/internal/ImportServiceTests.java index 4876dc8f3c..87710cda57 100644 --- a/app/server/appsmith-server/src/test/java/com/appsmith/server/imports/internal/ImportServiceTests.java +++ b/app/server/appsmith-server/src/test/java/com/appsmith/server/imports/internal/ImportServiceTests.java @@ -108,6 +108,9 @@ import reactor.test.StepVerifier; import reactor.util.function.Tuple3; import reactor.util.function.Tuple4; +import java.net.URISyntaxException; +import java.net.URL; +import java.nio.file.Path; import java.time.Duration; import java.time.Instant; import java.util.ArrayList; @@ -5191,4 +5194,143 @@ public class ImportServiceTests { }) .verifyComplete(); } + + @Test + @WithUserDetails(value = "api_user") + public void importApplication_WhenUpdateLayoutFailures_Success() throws URISyntaxException { + FilePart filePart = createFilePartWithIdenticalPackageStructure("faulty-dsl.json"); + + Workspace newWorkspace = new Workspace(); + newWorkspace.setName("Template Workspace"); + + Mono workspaceMono = workspaceService.create(newWorkspace).cache(); + + final Mono resultMono = workspaceMono + .flatMap(workspace -> + importService.extractArtifactExchangeJsonAndSaveArtifact(filePart, workspace.getId(), null)) + .map(importableArtifactDTO -> (ApplicationImportDTO) importableArtifactDTO); + + List permissionGroups = workspaceMono + .flatMapMany(savedWorkspace -> { + Set defaultPermissionGroups = savedWorkspace.getDefaultPermissionGroups(); + return permissionGroupRepository.findAllById(defaultPermissionGroups); + }) + .collectList() + .block(); + + PermissionGroup adminPermissionGroup = permissionGroups.stream() + .filter(permissionGroup -> permissionGroup.getName().startsWith(FieldName.ADMINISTRATOR)) + .findFirst() + .get(); + + PermissionGroup developerPermissionGroup = permissionGroups.stream() + .filter(permissionGroup -> permissionGroup.getName().startsWith(FieldName.DEVELOPER)) + .findFirst() + .get(); + + PermissionGroup viewerPermissionGroup = permissionGroups.stream() + .filter(permissionGroup -> permissionGroup.getName().startsWith(FieldName.VIEWER)) + .findFirst() + .get(); + + Policy manageAppPolicy = Policy.builder() + .permission(MANAGE_APPLICATIONS.getValue()) + .permissionGroups(Set.of(adminPermissionGroup.getId(), developerPermissionGroup.getId())) + .build(); + Policy readAppPolicy = Policy.builder() + .permission(READ_APPLICATIONS.getValue()) + .permissionGroups(Set.of( + adminPermissionGroup.getId(), developerPermissionGroup.getId(), viewerPermissionGroup.getId())) + .build(); + + StepVerifier.create(resultMono.flatMap(applicationImportDTO -> { + Application application = applicationImportDTO.getApplication(); + return Mono.zip( + Mono.just(applicationImportDTO), + datasourceService + .getAllByWorkspaceIdWithStorages( + application.getWorkspaceId(), Optional.of(MANAGE_DATASOURCES)) + .collectList(), + newActionService + .findAllByApplicationIdAndViewMode(application.getId(), false, READ_ACTIONS, null) + .collectList(), + newPageService + .findByApplicationId(application.getId(), MANAGE_PAGES, false) + .collectList(), + actionCollectionService + .findAllByApplicationIdAndViewMode(application.getId(), false, MANAGE_ACTIONS, null) + .collectList()); + })) + .assertNext(tuple -> { + final Application application = tuple.getT1().getApplication(); + final List unConfiguredDatasourceList = + tuple.getT1().getUnConfiguredDatasourceList(); + final boolean isPartialImport = tuple.getT1().getIsPartialImport(); + final List datasourceList = tuple.getT2(); + final List actionList = tuple.getT3(); + final List pageList = tuple.getT4(); + final List actionCollectionList = tuple.getT5(); + + assertThat(application.getName()).isEqualTo("faultDSL"); + assertThat(application.getWorkspaceId()).isNotNull(); + assertThat(application.getPages()).hasSize(1); + assertThat(application.getPolicies()).containsAll(Set.of(manageAppPolicy, readAppPolicy)); + assertThat(application.getPublishedPages()).hasSize(0); + assertThat(application.getModifiedBy()).isEqualTo("api_user"); + assertThat(application.getUpdatedAt()).isNotNull(); + assertThat(application.getEditModeThemeId()).isNotNull(); + assertThat(application.getPublishedModeThemeId()).isNotNull(); + assertThat(isPartialImport).isEqualTo(Boolean.TRUE); + assertThat(unConfiguredDatasourceList.size()).isNotEqualTo(0); + + assertThat(datasourceList).isNotEmpty(); + List datasourceNames = unConfiguredDatasourceList.stream() + .map(Datasource::getName) + .collect(Collectors.toList()); + assertThat(datasourceNames).contains("Mock_DB"); + + List collectionIdInAction = new ArrayList<>(); + assertThat(actionList).isNotEmpty(); + actionList.forEach(newAction -> { + ActionDTO actionDTO = newAction.getUnpublishedAction(); + assertThat(actionDTO.getPageId()) + .isNotEqualTo(pageList.get(0).getName()); + if (!StringUtils.isEmpty(actionDTO.getCollectionId())) { + collectionIdInAction.add(actionDTO.getCollectionId()); + } + }); + + assertThat(actionCollectionList).isNotEmpty(); + assertThat(actionCollectionList).hasSize(1); + assertThat(pageList).hasSize(1); + + ApplicationPage defaultAppPage = application.getPages().stream() + .filter(ApplicationPage::getIsDefault) + .findFirst() + .orElse(null); + assertThat(defaultAppPage).isNotNull(); + + PageDTO defaultPageDTO = pageList.stream() + .filter(pageDTO -> pageDTO.getId().equals(defaultAppPage.getId())) + .findFirst() + .orElse(null); + + assertThat(defaultPageDTO).isNotNull(); + }) + .verifyComplete(); + } + + // this would be the newer way to create the fileParts + private FilePart createFilePartWithIdenticalPackageStructure(String filePath) throws URISyntaxException { + FilePart filepart = Mockito.mock(FilePart.class, Mockito.RETURNS_DEEP_STUBS); + URL resource = this.getClass().getResource(filePath); + Flux dataBufferFlux = DataBufferUtils.read( + Path.of(resource.toURI()), new DefaultDataBufferFactory(), 4096) + .cache(); + + Mockito.when(filepart.content()).thenReturn(dataBufferFlux); + Mockito.when(filepart.headers().getContentType()).thenReturn(MediaType.APPLICATION_JSON); + + return filepart; + } } diff --git a/app/server/appsmith-server/src/test/java/com/appsmith/server/services/ActionCollectionServiceImplTest.java b/app/server/appsmith-server/src/test/java/com/appsmith/server/services/ActionCollectionServiceImplTest.java index e548b95eaf..97d4f5fcca 100644 --- a/app/server/appsmith-server/src/test/java/com/appsmith/server/services/ActionCollectionServiceImplTest.java +++ b/app/server/appsmith-server/src/test/java/com/appsmith/server/services/ActionCollectionServiceImplTest.java @@ -125,6 +125,15 @@ public class ActionCollectionServiceImplTest { @MockBean private DefaultResourcesService actionCollectionDefaultResourcesService; + @MockBean + private DefaultResourcesService actionCollectionDtoDefaultResourcesService; + + @MockBean + private DefaultResourcesService newActionDefaultResourcesService; + + @MockBean + private DefaultResourcesService actionDTODefaultResourcesService; + @BeforeEach public void setUp() { applicationPermission = new ApplicationPermissionImpl(); @@ -140,7 +149,10 @@ public class ActionCollectionServiceImplTest { responseUtils, applicationPermission, actionPermission, - actionCollectionDefaultResourcesService); + actionCollectionDefaultResourcesService, + actionCollectionDtoDefaultResourcesService, + newActionDefaultResourcesService, + actionDTODefaultResourcesService); layoutCollectionService = new LayoutCollectionServiceImpl( newPageService, diff --git a/app/server/appsmith-server/src/test/java/com/appsmith/server/services/CurlImporterServiceTest.java b/app/server/appsmith-server/src/test/java/com/appsmith/server/services/CurlImporterServiceTest.java index 41ad9260e8..54ba24f855 100644 --- a/app/server/appsmith-server/src/test/java/com/appsmith/server/services/CurlImporterServiceTest.java +++ b/app/server/appsmith-server/src/test/java/com/appsmith/server/services/CurlImporterServiceTest.java @@ -482,7 +482,7 @@ public class CurlImporterServiceTest { // fetch branched action Mono branchedSavedActionMono = branchedResultMono.flatMap(actionDTO -> newActionService.findByBranchNameAndDefaultActionId( - "testBranch", actionDTO.getId(), AclPermission.MANAGE_ACTIONS)); + "testBranch", actionDTO.getId(), false, AclPermission.MANAGE_ACTIONS)); StepVerifier.create(Mono.zip(branchedResultMono, branchedPageMono, branchedSavedActionMono)) .assertNext(tuple -> { diff --git a/app/server/appsmith-server/src/test/java/com/appsmith/server/services/ce/ActionServiceCE_Test.java b/app/server/appsmith-server/src/test/java/com/appsmith/server/services/ce/ActionServiceCE_Test.java index ea63f3af68..b840d25b85 100644 --- a/app/server/appsmith-server/src/test/java/com/appsmith/server/services/ce/ActionServiceCE_Test.java +++ b/app/server/appsmith-server/src/test/java/com/appsmith/server/services/ce/ActionServiceCE_Test.java @@ -315,7 +315,7 @@ public class ActionServiceCE_Test { Mono actionMono = layoutActionService .createSingleActionWithBranch(action, branchName) .flatMap(createdAction -> newActionService.findByBranchNameAndDefaultActionId( - branchName, createdAction.getId(), READ_ACTIONS)); + branchName, createdAction.getId(), false, READ_ACTIONS)); StepVerifier.create(actionMono) .assertNext(newAction -> { diff --git a/app/server/appsmith-server/src/test/java/com/appsmith/server/solutions/ce/ActionExecutionSolutionCEImplTest.java b/app/server/appsmith-server/src/test/java/com/appsmith/server/solutions/ce/ActionExecutionSolutionCEImplTest.java index 509520214c..8aaac8bc4c 100644 --- a/app/server/appsmith-server/src/test/java/com/appsmith/server/solutions/ce/ActionExecutionSolutionCEImplTest.java +++ b/app/server/appsmith-server/src/test/java/com/appsmith/server/solutions/ce/ActionExecutionSolutionCEImplTest.java @@ -264,20 +264,20 @@ class ActionExecutionSolutionCEImplTest { public void testExecuteAPIWithUsualOrderingOfTheParts() { String usualOrderOfParts = """ - --boundary\r - Content-Disposition: form-data; name="executeActionDTO"\r - \r - {"actionId":"63285a3388e48972c7519b18","viewMode":false,"paramProperties":{"k0":{"datatype": "string"}}}\r - --boundary\r - Content-Disposition: form-data; name="parameterMap"\r - \r - {"Input1.text":"k0"}\r - --boundary\r - Content-Disposition: form-data; name="k0"; filename="blob"\r - Content-Type: text/plain\r - \r - xyz\r - --boundary--"""; + --boundary\r + Content-Disposition: form-data; name="executeActionDTO"\r + \r + {"actionId":"63285a3388e48972c7519b18","viewMode":false,"paramProperties":{"k0":{"datatype": "string"}}}\r + --boundary\r + Content-Disposition: form-data; name="parameterMap"\r + \r + {"Input1.text":"k0"}\r + --boundary\r + Content-Disposition: form-data; name="k0"; filename="blob"\r + Content-Type: text/plain\r + \r + xyz\r + --boundary--"""; MockServerHttpRequest mock = MockServerHttpRequest.method(HttpMethod.POST, URI.create("https://example.com")) .contentType(new MediaType("multipart", "form-data", Map.of("boundary", "boundary"))) @@ -306,7 +306,9 @@ class ActionExecutionSolutionCEImplTest { .getTrueEnvironmentId( any(), any(), any(), Mockito.eq(environmentPermission.getExecutePermission()), anyBoolean()); doReturn(Mono.just(mockResult)).when(executionSolutionSpy).executeAction(any(), any()); - doReturn(Mono.just(newAction)).when(newActionService).findByBranchNameAndDefaultActionId(any(), any(), any()); + doReturn(Mono.just(newAction)) + .when(newActionService) + .findByBranchNameAndDefaultActionId(any(), any(), Mockito.anyBoolean(), any()); StepVerifier.create(actionExecutionResultMono) .assertNext(response -> { @@ -322,20 +324,20 @@ class ActionExecutionSolutionCEImplTest { public void testExecuteAPIWithParameterMapAsLastPart() { String parameterMapAtLast = """ - --boundary\r - Content-Disposition: form-data; name="executeActionDTO"\r - \r - {"actionId":"63285a3388e48972c7519b18","viewMode":false,"paramProperties":{"k0":{"datatype": "string"}}}\r - --boundary\r - Content-Disposition: form-data; name="k0"; filename="blob"\r - Content-Type: text/plain\r - \r - xyz\r - --boundary\r - Content-Disposition: form-data; name="parameterMap"\r - \r - {"Input1.text":"k0"}\r - --boundary--"""; + --boundary\r + Content-Disposition: form-data; name="executeActionDTO"\r + \r + {"actionId":"63285a3388e48972c7519b18","viewMode":false,"paramProperties":{"k0":{"datatype": "string"}}}\r + --boundary\r + Content-Disposition: form-data; name="k0"; filename="blob"\r + Content-Type: text/plain\r + \r + xyz\r + --boundary\r + Content-Disposition: form-data; name="parameterMap"\r + \r + {"Input1.text":"k0"}\r + --boundary--"""; MockServerHttpRequest mock = MockServerHttpRequest.method(HttpMethod.POST, URI.create("https://example.com")) .contentType(new MediaType("multipart", "form-data", Map.of("boundary", "boundary"))) @@ -364,7 +366,9 @@ class ActionExecutionSolutionCEImplTest { .getTrueEnvironmentId( any(), any(), any(), Mockito.eq(environmentPermission.getExecutePermission()), anyBoolean()); doReturn(Mono.just(mockResult)).when(executionSolutionSpy).executeAction(any(), any()); - doReturn(Mono.just(newAction)).when(newActionService).findByBranchNameAndDefaultActionId(any(), any(), any()); + doReturn(Mono.just(newAction)) + .when(newActionService) + .findByBranchNameAndDefaultActionId(any(), any(), Mockito.anyBoolean(), any()); StepVerifier.create(actionExecutionResultMono) .assertNext(response -> { @@ -380,25 +384,25 @@ class ActionExecutionSolutionCEImplTest { public void testParsePartsAndGetParamsFlux_withBlobIdentifiers_replacesValueInParam() { String partsWithBlobRefs = """ - --boundary\r - Content-Disposition: form-data; name="executeActionDTO"\r - \r - {"actionId":"63285a3388e48972c7519b18","viewMode":false,"paramProperties":{"k0":{"datatype": "string", "blobIdentifiers": ["blob:12345678-1234-1234-1234-123456781234"]}}}\r - --boundary\r - Content-Disposition: form-data; name="parameterMap"\r - \r - {"Input1.text":"k0"}\r - --boundary\r - Content-Disposition: form-data; name="k0"; filename="blob"\r - Content-Type: text/plain\r - \r - {"name": "randomName", "data": "blob:12345678-1234-1234-1234-123456781234"}\r - --boundary\r - Content-Disposition: form-data; name="blob:12345678-1234-1234-1234-123456781234"; filename="blob"\r - Content-Type: text/plain\r - \r - xy\\nz\r - --boundary--"""; + --boundary\r + Content-Disposition: form-data; name="executeActionDTO"\r + \r + {"actionId":"63285a3388e48972c7519b18","viewMode":false,"paramProperties":{"k0":{"datatype": "string", "blobIdentifiers": ["blob:12345678-1234-1234-1234-123456781234"]}}}\r + --boundary\r + Content-Disposition: form-data; name="parameterMap"\r + \r + {"Input1.text":"k0"}\r + --boundary\r + Content-Disposition: form-data; name="k0"; filename="blob"\r + Content-Type: text/plain\r + \r + {"name": "randomName", "data": "blob:12345678-1234-1234-1234-123456781234"}\r + --boundary\r + Content-Disposition: form-data; name="blob:12345678-1234-1234-1234-123456781234"; filename="blob"\r + Content-Type: text/plain\r + \r + xy\\nz\r + --boundary--"""; MockServerHttpRequest mock = MockServerHttpRequest.method(HttpMethod.POST, URI.create("https://example.com")) .contentType(new MediaType("multipart", "form-data", Map.of("boundary", "boundary"))) diff --git a/app/server/appsmith-server/src/test/resources/com/appsmith/server/imports/internal/faulty-dsl.json b/app/server/appsmith-server/src/test/resources/com/appsmith/server/imports/internal/faulty-dsl.json new file mode 100644 index 0000000000..68f2e5e599 --- /dev/null +++ b/app/server/appsmith-server/src/test/resources/com/appsmith/server/imports/internal/faulty-dsl.json @@ -0,0 +1,4713 @@ +{ + "artifactJsonType": "APPLICATION", + "clientSchemaVersion": 1.0, + "serverSchemaVersion": 7.0, + "exportedApplication": { + "name": "faultDSL", + "isPublic": false, + "pages": [{ "id": "Admin", "isDefault": true }], + "publishedPages": [{ "isDefault": true }], + "viewMode": false, + "appIsExample": false, + "unreadCommentThreads": 0.0, + "unpublishedApplicationDetail": { "appPositioning": { "type": "FIXED" } }, + "publishedApplicationDetail": { "appPositioning": { "type": "FIXED" } }, + "color": "#C7F3F0", + "icon": "website", + "slug": "faultdsl", + "unpublishedCustomJSLibs": [ + { + "uidString": "xmlParser_https://cdnjs.cloudflare.com/ajax/libs/fast-xml-parser/3.17.5/parser.min.js" + } + ], + "publishedCustomJSLibs": [], + "evaluationVersion": 2.0, + "applicationVersion": 2.0, + "collapseInvisibleWidgets": true, + "isManualUpdate": false, + "deleted": false + }, + "datasourceList": [ + { + "datasourceConfiguration": { + "connection": { + "mode": "READ_WRITE", + "ssl": { "authType": "DEFAULT" } + }, + "endpoints": [ + { "host": "mockdb.internal.appsmith.com", "port": 5432.0 } + ] + }, + "name": "Mock_DB", + "pluginId": "postgres-plugin", + "messages": [], + "isAutoGenerated": false, + "isTemplate": true, + "deleted": false, + "gitSyncId": "61b6d49e33c6ae6163af2716_62a720d884b913372519bc5e" + } + ], + "customJSLibList": [ + { + "name": "xmlParser", + "uidString": "xmlParser_https://cdnjs.cloudflare.com/ajax/libs/fast-xml-parser/3.17.5/parser.min.js", + "accessor": ["xmlParser"], + "url": "https://cdnjs.cloudflare.com/ajax/libs/fast-xml-parser/3.17.5/parser.min.js", + "version": "3.17.5", + "defs": "{\"!name\":\"LIB/xmlParser\",\"xmlParser\":{\"parse\":{\"!type\":\"fn()\",\"prototype\":{}},\"convertTonimn\":{\"!type\":\"fn()\",\"prototype\":{}},\"getTraversalObj\":{\"!type\":\"fn()\",\"prototype\":{}},\"convertToJson\":{\"!type\":\"fn()\",\"prototype\":{}},\"convertToJsonString\":{\"!type\":\"fn()\",\"prototype\":{}},\"validate\":{\"!type\":\"fn()\",\"prototype\":{}},\"j2xParser\":{\"!type\":\"fn()\",\"prototype\":{\"parse\":{\"!type\":\"fn()\",\"prototype\":{}},\"j2x\":{\"!type\":\"fn()\",\"prototype\":{}}}},\"parseToNimn\":{\"!type\":\"fn()\",\"prototype\":{}}}}", + "deleted": false, + "policies": [], + "userPermissions": [] + } + ], + "pageList": [ + { + "unpublishedPage": { + "name": "Admin", + "slug": "admin", + "layouts": [ + { + "viewMode": false, + "dsl": { + "widgetName": "MainContainer", + "backgroundColor": "none", + "rightColumn": 1160.0, + "snapColumns": 64.0, + "detachFromLayout": true, + "widgetId": "0", + "topRow": 0.0, + "bottomRow": 1080.0, + "containerStyle": "none", + "snapRows": 66.0, + "parentRowSpace": 1.0, + "type": "CANVAS_WIDGET", + "canExtend": true, + "version": 89.0, + "minHeight": 670.0, + "parentColumnSpace": 1.0, + "dynamicBindingPathList": [], + "leftColumn": 0.0, + "children": [ + { + "boxShadow": "none", + "widgetName": "Container2CopyCopy1", + "borderColor": "transparent", + "isCanvas": true, + "displayName": "Container", + "iconSVG": "/static/media/icon.1977dca3370505e2db3a8e44cfd54907.svg", + "searchTags": ["div", "parent", "group"], + "topRow": 27.0, + "bottomRow": 42.0, + "parentRowSpace": 10.0, + "type": "CONTAINER_WIDGET", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 19.8125, + "dynamicTriggerPathList": [], + "leftColumn": 15.0, + "dynamicBindingPathList": [], + "children": [ + { + "boxShadow": "none", + "widgetName": "Canvas2CopyCopy", + "displayName": "Canvas", + "topRow": 0.0, + "bottomRow": 150.0, + "parentRowSpace": 1.0, + "type": "CANVAS_WIDGET", + "canExtend": false, + "hideCard": true, + "minHeight": 150.0, + "parentColumnSpace": 1.0, + "leftColumn": 0.0, + "dynamicBindingPathList": [], + "children": [ + { + "boxShadow": "none", + "widgetName": "Image4CopyCopy", + "displayName": "Image", + "iconSVG": "/static/media/icon.52d8fb963abcb95c79b10f1553389f22.svg", + "topRow": 0.0, + "bottomRow": 5.0, + "parentRowSpace": 10.0, + "type": "IMAGE_WIDGET", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 19.8125, + "dynamicTriggerPathList": [], + "imageShape": "RECTANGLE", + "leftColumn": 0.0, + "dynamicBindingPathList": [{ "key": "borderRadius" }], + "defaultImage": "https://s3.us-east-2.amazonaws.com/template.appsmith.com/group-1000004181.svg", + "key": "6j28hyj8ew", + "image": "", + "isDeprecated": false, + "rightColumn": 13.0, + "objectFit": "contain", + "widgetId": "qfjwgwe05v", + "isVisible": true, + "version": 1.0, + "parentId": "w0jg0594ue", + "renderMode": "CANVAS", + "isLoading": false, + "maxZoomLevel": 1.0, + "enableDownload": false, + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}", + "enableRotation": false + }, + { + "widgetName": "Text1CopyCopyCopy", + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b523e6f70ba6f40a10fc2c7c5b5.svg", + "searchTags": ["typography", "paragraph", "label"], + "topRow": 9.0, + "bottomRow": 13.0, + "parentRowSpace": 10.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "overflow": "NONE", + "fontFamily": "{{appsmith.theme.fontFamily.appFont}}", + "parentColumnSpace": 4.3310546875, + "dynamicTriggerPathList": [], + "leftColumn": 0.0, + "dynamicBindingPathList": [ + { "key": "text" }, + { "key": "fontFamily" } + ], + "shouldTruncate": false, + "text": "{{appsmith.store.completedCount}}", + "key": "8ao8442ejy", + "isDeprecated": false, + "rightColumn": 47.0, + "textAlign": "LEFT", + "dynamicHeight": "FIXED", + "widgetId": "6fvp0cwnnf", + "isVisible": true, + "fontStyle": "BOLD", + "textColor": "#231F20", + "version": 1.0, + "parentId": "w0jg0594ue", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}", + "maxDynamicHeight": 9000.0, + "fontSize": "1.875rem", + "minDynamicHeight": 4.0 + }, + { + "widgetName": "Text1Copy1Copy", + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b523e6f70ba6f40a10fc2c7c5b5.svg", + "searchTags": ["typography", "paragraph", "label"], + "topRow": 5.0, + "bottomRow": 9.0, + "parentRowSpace": 10.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "overflow": "NONE", + "fontFamily": "{{appsmith.theme.fontFamily.appFont}}", + "parentColumnSpace": 4.3310546875, + "dynamicTriggerPathList": [], + "leftColumn": 0.0, + "dynamicBindingPathList": [{ "key": "fontFamily" }], + "shouldTruncate": false, + "text": "Completed", + "key": "8ao8442ejy", + "isDeprecated": false, + "rightColumn": 47.0, + "textAlign": "LEFT", + "dynamicHeight": "FIXED", + "widgetId": "h7p3oz17ig", + "isVisible": true, + "fontStyle": "", + "textColor": "#231F20", + "version": 1.0, + "parentId": "w0jg0594ue", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}", + "maxDynamicHeight": 9000.0, + "fontSize": "1.25rem", + "minDynamicHeight": 4.0 + } + ], + "key": "iv16tz47h6", + "isDeprecated": false, + "rightColumn": 475.5, + "detachFromLayout": true, + "widgetId": "w0jg0594ue", + "accentColor": "{{appsmith.theme.colors.primaryColor}}", + "containerStyle": "none", + "isVisible": true, + "version": 1.0, + "parentId": "aryazglzwa", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}" + } + ], + "borderWidth": "1", + "key": "i2gkdaesc8", + "backgroundColor": "#E6E9F5", + "isDeprecated": false, + "rightColumn": 30.0, + "dynamicHeight": "FIXED", + "widgetId": "aryazglzwa", + "containerStyle": "card", + "isVisible": true, + "version": 1.0, + "parentId": "0", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "Container2Copy", + "borderColor": "transparent", + "isCanvas": true, + "displayName": "Container", + "iconSVG": "/static/media/icon.1977dca3370505e2db3a8e44cfd54907.svg", + "searchTags": ["div", "parent", "group"], + "topRow": 10.0, + "bottomRow": 25.0, + "parentRowSpace": 10.0, + "type": "CONTAINER_WIDGET", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 19.8125, + "dynamicTriggerPathList": [], + "leftColumn": 15.0, + "dynamicBindingPathList": [], + "children": [ + { + "boxShadow": "none", + "widgetName": "Canvas2Copy", + "displayName": "Canvas", + "topRow": 0.0, + "bottomRow": 150.0, + "parentRowSpace": 1.0, + "type": "CANVAS_WIDGET", + "canExtend": false, + "hideCard": true, + "minHeight": 150.0, + "parentColumnSpace": 1.0, + "leftColumn": 0.0, + "dynamicBindingPathList": [], + "children": [ + { + "boxShadow": "none", + "widgetName": "Image4Copy", + "displayName": "Image", + "iconSVG": "/static/media/icon.52d8fb963abcb95c79b10f1553389f22.svg", + "topRow": 0.0, + "bottomRow": 5.0, + "parentRowSpace": 10.0, + "type": "IMAGE_WIDGET", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 19.8125, + "dynamicTriggerPathList": [], + "imageShape": "RECTANGLE", + "leftColumn": 0.0, + "dynamicBindingPathList": [{ "key": "borderRadius" }], + "defaultImage": "https://s3.us-east-2.amazonaws.com/template.appsmith.com/group-1000004180.svg", + "key": "6j28hyj8ew", + "image": "", + "isDeprecated": false, + "rightColumn": 11.0, + "objectFit": "contain", + "widgetId": "sy10nyyznt", + "isVisible": true, + "version": 1.0, + "parentId": "ijzsvhm730", + "renderMode": "CANVAS", + "isLoading": false, + "maxZoomLevel": 1.0, + "enableDownload": false, + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}", + "enableRotation": false + }, + { + "widgetName": "Text1CopyCopy", + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b523e6f70ba6f40a10fc2c7c5b5.svg", + "searchTags": ["typography", "paragraph", "label"], + "topRow": 9.0, + "bottomRow": 13.0, + "parentRowSpace": 10.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "overflow": "NONE", + "fontFamily": "{{appsmith.theme.fontFamily.appFont}}", + "parentColumnSpace": 4.3310546875, + "dynamicTriggerPathList": [], + "leftColumn": 0.0, + "dynamicBindingPathList": [ + { "key": "text" }, + { "key": "fontFamily" } + ], + "shouldTruncate": false, + "text": "{{appsmith.store.hoursSum}}", + "key": "8ao8442ejy", + "isDeprecated": false, + "rightColumn": 47.0, + "textAlign": "LEFT", + "dynamicHeight": "FIXED", + "widgetId": "hcxltom53y", + "isVisible": true, + "fontStyle": "BOLD", + "textColor": "#231F20", + "version": 1.0, + "parentId": "ijzsvhm730", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}", + "maxDynamicHeight": 9000.0, + "fontSize": "1.875rem", + "minDynamicHeight": 4.0 + }, + { + "widgetName": "Text1Copy1", + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b523e6f70ba6f40a10fc2c7c5b5.svg", + "searchTags": ["typography", "paragraph", "label"], + "topRow": 5.0, + "bottomRow": 9.0, + "parentRowSpace": 10.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "overflow": "NONE", + "fontFamily": "{{appsmith.theme.fontFamily.appFont}}", + "parentColumnSpace": 4.3310546875, + "dynamicTriggerPathList": [], + "leftColumn": 0.0, + "dynamicBindingPathList": [{ "key": "fontFamily" }], + "shouldTruncate": false, + "text": "Total Hours", + "key": "8ao8442ejy", + "isDeprecated": false, + "rightColumn": 63.0, + "textAlign": "LEFT", + "dynamicHeight": "FIXED", + "widgetId": "eie7hl9s3v", + "isVisible": true, + "fontStyle": "", + "textColor": "#231F20", + "version": 1.0, + "parentId": "ijzsvhm730", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}", + "maxDynamicHeight": 9000.0, + "fontSize": "1.25rem", + "minDynamicHeight": 4.0 + } + ], + "key": "iv16tz47h6", + "isDeprecated": false, + "rightColumn": 475.5, + "detachFromLayout": true, + "widgetId": "ijzsvhm730", + "accentColor": "{{appsmith.theme.colors.primaryColor}}", + "containerStyle": "none", + "isVisible": true, + "version": 1.0, + "parentId": "5m9lcia6q3", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}" + } + ], + "borderWidth": "1", + "key": "i2gkdaesc8", + "backgroundColor": "#E6E9F5", + "isDeprecated": false, + "rightColumn": 30.0, + "dynamicHeight": "FIXED", + "widgetId": "5m9lcia6q3", + "containerStyle": "card", + "isVisible": true, + "version": 1.0, + "parentId": "0", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "HeadingCopy", + "dynamicPropertyPathList": [{ "key": "fontSize" }], + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b52.svg", + "topRow": 2.0, + "bottomRow": 6.0, + "parentRowSpace": 10.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 16.62109375, + "dynamicTriggerPathList": [], + "overflow": "NONE", + "fontFamily": "System Default", + "leftColumn": 15.0, + "dynamicBindingPathList": [], + "truncateButtonColor": "#FFC13D", + "text": "Work Orders", + "key": "czyq0gtp0e", + "labelTextSize": "0.875rem", + "rightColumn": 52.0, + "textAlign": "LEFT", + "dynamicHeight": "FIXED", + "widgetId": "cxkv9q70wz", + "isVisible": true, + "fontStyle": "BOLD", + "textColor": "#003B4A", + "version": 1.0, + "parentId": "0", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "fontSize": "1.7rem", + "minDynamicHeight": 4.0 + }, + { + "widgetName": "Text1", + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b523e6f70ba6f40a10fc2c7c5b5.svg", + "searchTags": ["typography", "paragraph", "label"], + "topRow": 6.0, + "bottomRow": 10.0, + "parentRowSpace": 10.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "overflow": "NONE", + "fontFamily": "{{appsmith.theme.fontFamily.appFont}}", + "parentColumnSpace": 19.8125, + "dynamicTriggerPathList": [], + "leftColumn": 15.0, + "dynamicBindingPathList": [{ "key": "fontFamily" }], + "shouldTruncate": false, + "truncateButtonColor": "{{appsmith.theme.colors.primaryColor}}", + "text": "Add and manage work orders", + "key": "p0uhc3c013", + "isDeprecated": false, + "rightColumn": 45.0, + "textAlign": "LEFT", + "dynamicHeight": "AUTO_HEIGHT", + "widgetId": "jify2p8j5i", + "isVisible": true, + "fontStyle": "", + "textColor": "#231F20", + "version": 1.0, + "parentId": "0", + "renderMode": "CANVAS", + "isLoading": false, + "originalTopRow": 6.0, + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}", + "maxDynamicHeight": 9000.0, + "originalBottomRow": 10.0, + "fontSize": "1rem", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "selectAgent", + "isFilterable": false, + "dynamicPropertyPathList": [ + { "key": "onOptionChange" }, + { "key": "sourceData" } + ], + "displayName": "Select", + "iconSVG": "/static/media/icon.bd99caba.svg", + "labelText": "", + "topRow": 46.0, + "bottomRow": 50.0, + "parentRowSpace": 10.0, + "type": "SELECT_WIDGET", + "serverSideFiltering": false, + "hideCard": false, + "defaultOptionValue": "", + "animateLoading": true, + "parentColumnSpace": 12.688995361328125, + "dynamicTriggerPathList": [{ "key": "onOptionChange" }], + "leftColumn": 17.0, + "dynamicBindingPathList": [ + { "key": "options" }, + { "key": "accentColor" } + ], + "placeholderText": "Agent", + "isDisabled": false, + "key": "fj5c87ojig", + "labelTextSize": "0.875rem", + "isRequired": false, + "rightColumn": 31.0, + "dynamicHeight": "FIXED", + "widgetId": "g84nip1mxz", + "accentColor": "{{appsmith.theme.colors.primaryColor}}", + "isVisible": true, + "version": 1.0, + "parentId": "0", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0.375rem", + "maxDynamicHeight": 9000.0, + "onOptionChange": "{{ \nselectAgent.selectedOptionValue.length > 0 ? select_work_ordersAgent.run().then(() => {\nJSObject1.totalHoursCalc();\nJSObject1.completedCalc();\nJSObject1.equipChart()\t\n}) : select_work_orders.run().then(() => {\nJSObject1.totalHoursCalc();\nJSObject1.completedCalc();\nJSObject1.equipChart()\t\n}) \n}}\n\n", + "minDynamicHeight": 4.0, + "sourceData": "[\n {\n \"label\": {{select_agent.data[0].agent}},\n \"value\": {{select_agent.data[0].agent}}\n },\n\t {\n \"label\": {{select_agent.data[2].agent}},\n \"value\": {{select_agent.data[2].agent}}\n },\n\t {\n \"label\": {{select_agent.data[3].agent}},\n \"value\": {{select_agent.data[3].agent}}\n },\n\t {\n \"label\": {{select_agent.data[4].agent}},\n \"value\": {{select_agent.data[4].agent}}\n },\n\t {\n \"label\": {{select_agent.data[1].agent}},\n \"value\": {{select_agent.data[1].agent}}\n }\n]", + "optionLabel": "label", + "optionValue": "value" + }, + { + "boxShadow": "none", + "isVisibleDownload": false, + "iconSVG": "/static/media/icon.db8a9cbd.svg", + "topRow": 51.0, + "isSortable": true, + "onPageChange": "{{selectAgent.selectedOptionValue ? select_work_ordersAgent.run() : select_work_orders.run()}}", + "type": "TABLE_WIDGET", + "animateLoading": true, + "dynamicBindingPathList": [ + { "key": "tableData" }, + { "key": "primaryColumns.customColumn1.boxShadow" }, + { "key": "primaryColumns.customColumn1.buttonColor" }, + { "key": "primaryColumns.customColumn1.buttonLabel" }, + { "key": "primaryColumns.mat_cost.computedValue" }, + { "key": "primaryColumns.total_cost.computedValue" }, + { "key": "primaryColumns.work_id.computedValue" }, + { "key": "primaryColumns.customer_email.computedValue" }, + { "key": "primaryColumns.customer_name.computedValue" }, + { "key": "primaryColumns.hours.computedValue" }, + { "key": "primaryColumns.completed.computedValue" }, + { "key": "primaryColumns.maintenance_notes.computedValue" }, + { "key": "primaryColumns.agent.computedValue" }, + { "key": "primaryColumns.request_date.computedValue" }, + { "key": "primaryColumns.description.computedValue" }, + { "key": "primaryColumns.category.computedValue" }, + { "key": "primaryColumns.equipment.computedValue" }, + { "key": "accentColor" }, + { "key": "derivedColumns.customColumn1.buttonLabel" }, + { "key": "derivedColumns.customColumn1.menuColor" }, + { "key": "primaryColumns.customColumn1.menuColor" }, + { "key": "derivedColumns.customColumn1.borderRadius" }, + { "key": "primaryColumns.customColumn1.borderRadius" }, + { "key": "derivedColumns.customColumn1.boxShadow" }, + { "key": "totalRecordsCount" } + ], + "leftColumn": 15.0, + "delimiter": ",", + "accentColor": "{{appsmith.theme.colors.primaryColor}}", + "isVisibleFilters": true, + "isVisible": true, + "enableClientSideSearch": false, + "version": 3.0, + "totalRecordsCount": "{{selectAgent.selectedOptionValue ? select_work_ordersAgentPage.data.length : select_work_ordersPage.data.length}}", + "isLoading": false, + "childStylesheet": { + "button": { + "buttonColor": "{{appsmith.theme.colors.primaryColor}}", + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}", + "boxShadow": "none" + }, + "menuButton": { + "menuColor": "{{appsmith.theme.colors.primaryColor}}", + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}", + "boxShadow": "none" + }, + "iconButton": { + "menuColor": "{{appsmith.theme.colors.primaryColor}}", + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}", + "boxShadow": "none" + } + }, + "borderRadius": "0px", + "columnSizeMap": { + "task": 245.0, + "step": 62.0, + "status": 75.0, + "customColumn1": 82.0, + "work_id": 85.0, + "category": 198.0, + "equipment": 124.0, + "completed": 124.0 + }, + "widgetName": "workOrdersTable", + "defaultPageSize": 0.0, + "columnOrder": [ + "work_id", + "equipment", + "category", + "description", + "request_date", + "agent", + "maintenance_notes", + "completed", + "hours", + "customer_name", + "customer_email", + "total_cost", + "mat_cost", + "customColumn1" + ], + "dynamicPropertyPathList": [ + { "key": "onPageChange" }, + { "key": "onRowSelected" } + ], + "displayName": "Table", + "bottomRow": 107.0, + "parentRowSpace": 10.0, + "defaultSelectedRow": "0", + "hideCard": false, + "parentColumnSpace": 6.4609375, + "dynamicTriggerPathList": [ + { "key": "onRowSelected" }, + { "key": "onPageChange" }, + { "key": "primaryColumns.customColumn1.onClick" } + ], + "primaryColumns": { + "equipment": { + "index": 0.0, + "width": 150.0, + "id": "equipment", + "horizontalAlignment": "LEFT", + "verticalAlignment": "CENTER", + "columnType": "text", + "textSize": "0.875rem", + "enableFilter": true, + "enableSort": true, + "isVisible": true, + "isDisabled": false, + "isCellVisible": true, + "isDerived": false, + "label": "Equipment", + "computedValue": "{{workOrdersTable.sanitizedTableData.map((currentRow) => ( currentRow.equipment))}}", + "cellBackground": "transparent", + "borderRadius": "0px", + "boxShadow": "none" + }, + "category": { + "index": 1.0, + "width": 150.0, + "id": "category", + "horizontalAlignment": "LEFT", + "verticalAlignment": "CENTER", + "columnType": "text", + "textSize": "0.875rem", + "enableFilter": true, + "enableSort": true, + "isVisible": true, + "isDisabled": false, + "isCellVisible": true, + "isDerived": false, + "label": "Category", + "computedValue": "{{workOrdersTable.sanitizedTableData.map((currentRow) => ( currentRow.category))}}", + "cellBackground": "transparent", + "borderRadius": "0px", + "boxShadow": "none" + }, + "description": { + "index": 2.0, + "width": 150.0, + "id": "description", + "horizontalAlignment": "LEFT", + "verticalAlignment": "CENTER", + "columnType": "text", + "textSize": "0.875rem", + "enableFilter": true, + "enableSort": true, + "isVisible": false, + "isDisabled": false, + "isCellVisible": true, + "isDerived": false, + "label": "description", + "computedValue": "{{workOrdersTable.sanitizedTableData.map((currentRow) => ( currentRow.description))}}", + "cellBackground": "transparent", + "borderRadius": "0px", + "boxShadow": "none" + }, + "request_date": { + "index": 3.0, + "width": 150.0, + "id": "request_date", + "horizontalAlignment": "LEFT", + "verticalAlignment": "CENTER", + "columnType": "date", + "textSize": "0.875rem", + "enableFilter": true, + "enableSort": true, + "isVisible": true, + "isDisabled": false, + "isCellVisible": true, + "isDerived": false, + "label": "Date", + "computedValue": "{{workOrdersTable.sanitizedTableData.map((currentRow) => ( currentRow.request_date))}}", + "cellBackground": "transparent", + "borderRadius": "0px", + "boxShadow": "none", + "iconName": "", + "outputFormat": "DD/MM/YYYY" + }, + "agent": { + "index": 4.0, + "width": 150.0, + "id": "agent", + "horizontalAlignment": "LEFT", + "verticalAlignment": "CENTER", + "columnType": "text", + "textSize": "0.875rem", + "enableFilter": true, + "enableSort": true, + "isVisible": true, + "isDisabled": false, + "isCellVisible": true, + "isDerived": false, + "label": "Agent", + "computedValue": "{{workOrdersTable.sanitizedTableData.map((currentRow) => ( currentRow.agent))}}", + "cellBackground": "transparent", + "borderRadius": "0px", + "boxShadow": "none" + }, + "maintenance_notes": { + "index": 5.0, + "width": 150.0, + "id": "maintenance_notes", + "horizontalAlignment": "LEFT", + "verticalAlignment": "CENTER", + "columnType": "text", + "textSize": "0.875rem", + "enableFilter": true, + "enableSort": true, + "isVisible": false, + "isDisabled": false, + "isCellVisible": true, + "isDerived": false, + "label": "maintenance_notes", + "computedValue": "{{workOrdersTable.sanitizedTableData.map((currentRow) => ( currentRow.maintenance_notes))}}", + "cellBackground": "transparent", + "borderRadius": "0px", + "boxShadow": "none" + }, + "completed": { + "index": 6.0, + "width": 150.0, + "id": "completed", + "horizontalAlignment": "LEFT", + "verticalAlignment": "CENTER", + "columnType": "text", + "textSize": "0.875rem", + "enableFilter": true, + "enableSort": true, + "isVisible": true, + "isDisabled": false, + "isCellVisible": true, + "isDerived": false, + "label": "Completed?", + "computedValue": "{{workOrdersTable.sanitizedTableData.map((currentRow) => ( currentRow.completed))}}", + "cellBackground": "transparent", + "borderRadius": "0px", + "boxShadow": "none" + }, + "hours": { + "index": 7.0, + "width": 150.0, + "id": "hours", + "horizontalAlignment": "LEFT", + "verticalAlignment": "CENTER", + "columnType": "text", + "textSize": "0.875rem", + "enableFilter": true, + "enableSort": true, + "isVisible": false, + "isDisabled": false, + "isCellVisible": true, + "isDerived": false, + "label": "Hours spent", + "computedValue": "{{workOrdersTable.sanitizedTableData.map((currentRow) => ( currentRow.hours))}}", + "cellBackground": "transparent", + "borderRadius": "0px", + "boxShadow": "none" + }, + "customer_name": { + "index": 8.0, + "width": 150.0, + "id": "customer_name", + "horizontalAlignment": "LEFT", + "verticalAlignment": "CENTER", + "columnType": "text", + "textSize": "0.875rem", + "enableFilter": true, + "enableSort": true, + "isVisible": false, + "isDisabled": false, + "isCellVisible": true, + "isDerived": false, + "label": "Customer Name", + "computedValue": "{{workOrdersTable.sanitizedTableData.map((currentRow) => ( currentRow.customer_name))}}", + "cellBackground": "transparent", + "borderRadius": "0px", + "boxShadow": "none" + }, + "customer_email": { + "index": 9.0, + "width": 150.0, + "id": "customer_email", + "horizontalAlignment": "LEFT", + "verticalAlignment": "CENTER", + "columnType": "text", + "textSize": "0.875rem", + "enableFilter": true, + "enableSort": true, + "isVisible": false, + "isDisabled": false, + "isCellVisible": true, + "isDerived": false, + "label": "Customer Email", + "computedValue": "{{workOrdersTable.sanitizedTableData.map((currentRow) => ( currentRow.customer_email))}}", + "cellBackground": "transparent", + "borderRadius": "0px", + "boxShadow": "none" + }, + "work_id": { + "index": 0.0, + "width": 150.0, + "id": "work_id", + "horizontalAlignment": "LEFT", + "verticalAlignment": "CENTER", + "columnType": "text", + "textSize": "0.875rem", + "enableFilter": true, + "enableSort": true, + "isVisible": true, + "isDisabled": false, + "isCellVisible": true, + "isDerived": false, + "label": "Work ID", + "computedValue": "{{workOrdersTable.sanitizedTableData.map((currentRow) => ( currentRow.work_id))}}", + "cellBackground": "transparent", + "borderRadius": "0px", + "boxShadow": "none" + }, + "total_cost": { + "index": 11.0, + "width": 150.0, + "id": "total_cost", + "horizontalAlignment": "LEFT", + "verticalAlignment": "CENTER", + "columnType": "text", + "textSize": "0.875rem", + "enableFilter": true, + "enableSort": true, + "isVisible": false, + "isDisabled": false, + "isCellVisible": true, + "isDerived": false, + "label": "Total Cost", + "computedValue": "{{workOrdersTable.sanitizedTableData.map((currentRow) => ( currentRow.total_cost))}}", + "cellBackground": "transparent", + "borderRadius": "0px", + "boxShadow": "none" + }, + "mat_cost": { + "index": 12.0, + "width": 150.0, + "id": "mat_cost", + "horizontalAlignment": "LEFT", + "verticalAlignment": "CENTER", + "columnType": "text", + "textSize": "0.875rem", + "enableFilter": true, + "enableSort": true, + "isVisible": false, + "isDisabled": false, + "isCellVisible": true, + "isDerived": false, + "label": "Material Cost", + "computedValue": "{{workOrdersTable.sanitizedTableData.map((currentRow) => ( currentRow.mat_cost))}}", + "cellBackground": "transparent", + "borderRadius": "0px", + "boxShadow": "none" + }, + "customColumn1": { + "index": 13.0, + "width": 150.0, + "id": "customColumn1", + "columnType": "iconButton", + "enableFilter": true, + "enableSort": true, + "isVisible": true, + "isDisabled": false, + "isCellVisible": true, + "isDerived": true, + "label": "Edit", + "computedValue": "", + "buttonStyle": "rgb(3, 179, 101)", + "labelColor": "#FFFFFF", + "buttonColor": "{{workOrdersTable.sanitizedTableData.map((currentRow) => ( appsmith.theme.colors.primaryColor))}}", + "borderRadius": "{{workOrdersTable.sanitizedTableData.map((currentRow) => ( appsmith.theme.borderRadius.appBorderRadius))}}", + "boxShadow": "{{workOrdersTable.sanitizedTableData.map((currentRow) => ( 'none'))}}", + "iconName": "edit", + "buttonLabel": "{{workOrdersTable.sanitizedTableData.map((currentRow) => ( 'Edit'))}}", + "buttonVariant": "TERTIARY", + "menuColor": "{{workOrdersTable.sanitizedTableData.map((currentRow) => ( appsmith.theme.colors.primaryColor))}}", + "onClick": "{{showModal('Modal1')}}", + "cellBackground": "transparent" + } + }, + "onRowSelected": "", + "key": "56eiocmwj5", + "derivedColumns": { + "customColumn1": { + "index": 13.0, + "width": 150.0, + "id": "customColumn1", + "columnType": "iconButton", + "enableFilter": true, + "enableSort": true, + "isVisible": true, + "isDisabled": false, + "isCellVisible": true, + "isDerived": true, + "label": "Edit", + "computedValue": "", + "buttonStyle": "rgb(3, 179, 101)", + "labelColor": "#FFFFFF", + "buttonColor": "{{workOrdersTable.sanitizedTableData.map((currentRow) => ( appsmith.theme.colors.primaryColor))}}", + "borderRadius": "{{workOrdersTable.sanitizedTableData.map((currentRow) => ( appsmith.theme.borderRadius.appBorderRadius))}}", + "boxShadow": "{{workOrdersTable.sanitizedTableData.map((currentRow) => ( 'none'))}}", + "iconName": "edit", + "buttonLabel": "{{workOrdersTable.sanitizedTableData.map((currentRow) => ( 'Edit'))}}", + "buttonVariant": "TERTIARY", + "menuColor": "{{workOrdersTable.sanitizedTableData.map((currentRow) => ( appsmith.theme.colors.primaryColor))}}", + "onClick": "{{showModal('Modal1')}}", + "cellBackground": "transparent" + } + }, + "labelTextSize": "0.875rem", + "rightColumn": 63.0, + "textSize": "0.875rem", + "widgetId": "ijijwwgerq", + "tableData": "{{selectAgent.selectedOptionValue.length != 0 ? select_work_ordersAgent.data : select_work_orders.data}}", + "label": "Data", + "searchKey": "", + "parentId": "0", + "serverSidePaginationEnabled": true, + "renderMode": "CANVAS", + "horizontalAlignment": "LEFT", + "isVisibleSearch": true, + "isVisiblePagination": true, + "cellBackground": "transparent", + "verticalAlignment": "CENTER" + }, + { + "boxShadow": "none", + "widgetName": "Container1", + "borderColor": "#E0DEDE", + "isCanvas": true, + "displayName": "Container", + "iconSVG": "/static/media/icon.1977dca3370505e2db3a8e44cfd54907.svg", + "searchTags": ["div", "parent", "group"], + "topRow": 0.0, + "bottomRow": 108.0, + "parentRowSpace": 10.0, + "type": "CONTAINER_WIDGET", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 19.8125, + "dynamicTriggerPathList": [], + "leftColumn": 0.0, + "dynamicBindingPathList": [], + "children": [ + { + "boxShadow": "none", + "widgetName": "Canvas1", + "displayName": "Canvas", + "topRow": 0.0, + "bottomRow": 1080.0, + "parentRowSpace": 1.0, + "type": "CANVAS_WIDGET", + "canExtend": false, + "hideCard": true, + "minHeight": 400.0, + "parentColumnSpace": 1.0, + "leftColumn": 0.0, + "dynamicBindingPathList": [], + "children": [ + { + "boxShadow": "none", + "widgetName": "Image2Copy2", + "displayName": "Image", + "iconSVG": "/static/media/icon.52d8fb963abcb95c79b10f1553389f22.svg", + "topRow": 28.0, + "bottomRow": 32.0, + "parentRowSpace": 10.0, + "type": "IMAGE_WIDGET", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 4.021484375, + "dynamicTriggerPathList": [], + "imageShape": "RECTANGLE", + "leftColumn": 4.0, + "dynamicBindingPathList": [{ "key": "borderRadius" }], + "defaultImage": "https://s3.us-east-2.amazonaws.com/template.appsmith.com/group-4394.svg", + "key": "20b6vlid8h", + "image": "", + "isDeprecated": false, + "rightColumn": 13.0, + "objectFit": "contain", + "widgetId": "3hphbu1n4x", + "isVisible": true, + "version": 1.0, + "parentId": "syjkq3pgjy", + "renderMode": "CANVAS", + "isLoading": false, + "maxZoomLevel": 1.0, + "enableDownload": false, + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}", + "enableRotation": false + }, + { + "resetFormOnClick": false, + "boxShadow": "none", + "widgetName": "Button2Copy2", + "onClick": "{{navigateTo('Admin', {}, 'SAME_WINDOW')}}", + "buttonColor": "transparent", + "displayName": "Button", + "iconSVG": "/static/media/icon.cca026338f1c8eb6df8ba03d084c2fca.svg", + "searchTags": ["click", "submit"], + "topRow": 28.0, + "bottomRow": 32.0, + "parentRowSpace": 10.0, + "type": "BUTTON_WIDGET", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 4.021484375, + "dynamicTriggerPathList": [{ "key": "onClick" }], + "leftColumn": 13.0, + "dynamicBindingPathList": [{ "key": "borderRadius" }], + "text": "Admin", + "isDisabled": false, + "key": "ea7apjwric", + "isDeprecated": false, + "rightColumn": 61.0, + "isDefaultClickDisabled": true, + "widgetId": "jspaw0xf26", + "isVisible": true, + "recaptchaType": "V3", + "version": 1.0, + "parentId": "syjkq3pgjy", + "renderMode": "CANVAS", + "isLoading": false, + "disabledWhenInvalid": false, + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}", + "buttonVariant": "PRIMARY", + "placement": "START" + }, + { + "boxShadow": "none", + "widgetName": "Image2Copy1", + "displayName": "Image", + "iconSVG": "/static/media/icon.52d8fb963abcb95c79b10f1553389f22.svg", + "topRow": 23.0, + "bottomRow": 27.0, + "parentRowSpace": 10.0, + "type": "IMAGE_WIDGET", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 4.021484375, + "dynamicTriggerPathList": [], + "imageShape": "RECTANGLE", + "leftColumn": 4.0, + "dynamicBindingPathList": [{ "key": "borderRadius" }], + "defaultImage": "https://s3.us-east-2.amazonaws.com/template.appsmith.com/files.svg", + "key": "20b6vlid8h", + "image": "", + "isDeprecated": false, + "rightColumn": 13.0, + "objectFit": "contain", + "widgetId": "b9qc3b3ueh", + "isVisible": true, + "version": 1.0, + "parentId": "syjkq3pgjy", + "renderMode": "CANVAS", + "isLoading": false, + "maxZoomLevel": 1.0, + "enableDownload": false, + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}", + "enableRotation": false + }, + { + "resetFormOnClick": false, + "boxShadow": "none", + "widgetName": "Button2Copy1", + "onClick": "{{navigateTo('My orders', {}, 'SAME_WINDOW')}}", + "buttonColor": "transparent", + "displayName": "Button", + "iconSVG": "/static/media/icon.cca026338f1c8eb6df8ba03d084c2fca.svg", + "searchTags": ["click", "submit"], + "topRow": 23.0, + "bottomRow": 27.0, + "parentRowSpace": 10.0, + "type": "BUTTON_WIDGET", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 4.021484375, + "dynamicTriggerPathList": [{ "key": "onClick" }], + "leftColumn": 13.0, + "dynamicBindingPathList": [{ "key": "borderRadius" }], + "text": "My Work Orders", + "isDisabled": false, + "key": "ea7apjwric", + "isDeprecated": false, + "rightColumn": 60.0, + "isDefaultClickDisabled": true, + "widgetId": "7qi044xx0w", + "isVisible": true, + "recaptchaType": "V3", + "version": 1.0, + "parentId": "syjkq3pgjy", + "renderMode": "CANVAS", + "isLoading": false, + "disabledWhenInvalid": false, + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}", + "buttonVariant": "PRIMARY", + "placement": "START" + }, + { + "boxShadow": "none", + "widgetName": "Image2Copy3", + "displayName": "Image", + "iconSVG": "/static/media/icon.52d8fb963abcb95c79b10f1553389f22.svg", + "topRow": 18.0, + "bottomRow": 22.0, + "parentRowSpace": 10.0, + "type": "IMAGE_WIDGET", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 4.021484375, + "dynamicTriggerPathList": [], + "imageShape": "RECTANGLE", + "leftColumn": 4.0, + "dynamicBindingPathList": [{ "key": "borderRadius" }], + "defaultImage": "https://s3.us-east-2.amazonaws.com/template.appsmith.com/listplus.svg", + "key": "20b6vlid8h", + "image": "", + "isDeprecated": false, + "rightColumn": 13.0, + "objectFit": "contain", + "widgetId": "z2rj62mi7h", + "isVisible": true, + "version": 1.0, + "parentId": "syjkq3pgjy", + "renderMode": "CANVAS", + "isLoading": false, + "maxZoomLevel": 1.0, + "enableDownload": false, + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}", + "enableRotation": false + }, + { + "resetFormOnClick": false, + "boxShadow": "none", + "widgetName": "Button2Copy3", + "onClick": "{{navigateTo('Submit new order', {}, 'SAME_WINDOW')}}", + "buttonColor": "transparent", + "displayName": "Button", + "iconSVG": "/static/media/icon.cca026338f1c8eb6df8ba03d084c2fca.svg", + "searchTags": ["click", "submit"], + "topRow": 18.0, + "bottomRow": 22.0, + "parentRowSpace": 10.0, + "type": "BUTTON_WIDGET", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 4.021484375, + "dynamicTriggerPathList": [{ "key": "onClick" }], + "leftColumn": 13.0, + "dynamicBindingPathList": [{ "key": "borderRadius" }], + "text": "New Work Request", + "isDisabled": false, + "key": "ea7apjwric", + "isDeprecated": false, + "rightColumn": 63.0, + "isDefaultClickDisabled": true, + "widgetId": "exs2k6maug", + "isVisible": true, + "recaptchaType": "V3", + "version": 1.0, + "parentId": "syjkq3pgjy", + "renderMode": "CANVAS", + "isLoading": false, + "disabledWhenInvalid": false, + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}", + "buttonVariant": "PRIMARY", + "placement": "START" + }, + { + "boxShadow": "none", + "widgetName": "Image1", + "displayName": "Image", + "iconSVG": "/static/media/icon.52d8fb963abcb95c79b10f1553389f22.svg", + "topRow": 1.0, + "bottomRow": 6.0, + "parentRowSpace": 10.0, + "type": "IMAGE_WIDGET", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 3.7119140625, + "dynamicTriggerPathList": [], + "imageShape": "RECTANGLE", + "leftColumn": 2.0, + "dynamicBindingPathList": [{ "key": "borderRadius" }], + "defaultImage": "https://s3.us-east-2.amazonaws.com/template.appsmith.com/group-4465.svg", + "key": "20b6vlid8h", + "image": "", + "isDeprecated": false, + "rightColumn": 39.0, + "objectFit": "contain", + "widgetId": "cccyinonx7", + "isVisible": true, + "version": 1.0, + "parentId": "syjkq3pgjy", + "renderMode": "CANVAS", + "isLoading": false, + "maxZoomLevel": 1.0, + "enableDownload": false, + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}", + "enableRotation": false + }, + { + "boxShadow": "none", + "widgetName": "Divider1", + "thickness": 2.0, + "displayName": "Divider", + "iconSVG": "/static/media/icon.cbe8f608ca868e1eb44607e5fbd4a9e5.svg", + "searchTags": ["line"], + "topRow": 6.0, + "bottomRow": 10.0, + "parentRowSpace": 10.0, + "type": "DIVIDER_WIDGET", + "capType": "nc", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 3.7119140625, + "dynamicTriggerPathList": [], + "leftColumn": 0.0, + "dynamicBindingPathList": [], + "key": "c3xzqeinqm", + "dividerColor": "#5E6C9E", + "orientation": "horizontal", + "strokeStyle": "solid", + "isDeprecated": false, + "rightColumn": 64.0, + "widgetId": "00rr0od1st", + "accentColor": "{{appsmith.theme.colors.primaryColor}}", + "capSide": 0.0, + "isVisible": true, + "version": 1.0, + "parentId": "syjkq3pgjy", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}" + }, + { + "boxShadow": "none", + "widgetName": "Image2Copy4", + "displayName": "Image", + "iconSVG": "/static/media/icon.52d8fb963abcb95c79b10f1553389f22.svg", + "topRow": 13.0, + "bottomRow": 17.0, + "parentRowSpace": 10.0, + "type": "IMAGE_WIDGET", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 4.021484375, + "dynamicTriggerPathList": [], + "imageShape": "RECTANGLE", + "leftColumn": 4.0, + "dynamicBindingPathList": [{ "key": "borderRadius" }], + "defaultImage": "https://s3.us-east-2.amazonaws.com/template.appsmith.com/group-4405.svg", + "key": "20b6vlid8h", + "image": "", + "isDeprecated": false, + "rightColumn": 13.0, + "objectFit": "contain", + "widgetId": "ynyek2ui5b", + "isVisible": true, + "version": 1.0, + "parentId": "syjkq3pgjy", + "renderMode": "CANVAS", + "isLoading": false, + "maxZoomLevel": 1.0, + "enableDownload": false, + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}", + "enableRotation": false + }, + { + "resetFormOnClick": false, + "boxShadow": "none", + "widgetName": "Button2", + "onClick": "{{navigateTo('Home Page', {}, 'SAME_WINDOW')}}", + "buttonColor": "transparent", + "displayName": "Button", + "iconSVG": "/static/media/icon.cca026338f1c8eb6df8ba03d084c2fca.svg", + "searchTags": ["click", "submit"], + "topRow": 13.0, + "bottomRow": 17.0, + "parentRowSpace": 10.0, + "type": "BUTTON_WIDGET", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 4.021484375, + "dynamicTriggerPathList": [{ "key": "onClick" }], + "leftColumn": 13.0, + "dynamicBindingPathList": [{ "key": "borderRadius" }], + "text": "Dashboard", + "isDisabled": false, + "key": "ea7apjwric", + "isDeprecated": false, + "rightColumn": 60.0, + "isDefaultClickDisabled": true, + "widgetId": "us1rl2o7qy", + "isVisible": true, + "recaptchaType": "V3", + "version": 1.0, + "parentId": "syjkq3pgjy", + "renderMode": "CANVAS", + "isLoading": false, + "disabledWhenInvalid": false, + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}", + "buttonVariant": "PRIMARY", + "placement": "START" + }, + { + "boxShadow": "none", + "widgetName": "Image3", + "displayName": "Image", + "iconSVG": "/static/media/icon.52d8fb963abcb95c79b10f1553389f22.svg", + "topRow": 83.0, + "bottomRow": 105.0, + "parentRowSpace": 10.0, + "type": "IMAGE_WIDGET", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 4.021484375, + "dynamicTriggerPathList": [], + "imageShape": "RECTANGLE", + "leftColumn": 0.0, + "dynamicBindingPathList": [], + "defaultImage": "https://s3.us-east-2.amazonaws.com/template.appsmith.com/bdd.png", + "key": "20b6vlid8h", + "image": "", + "isDeprecated": false, + "rightColumn": 64.0, + "objectFit": "contain", + "widgetId": "z3k3214q31", + "isVisible": true, + "version": 1.0, + "parentId": "syjkq3pgjy", + "renderMode": "CANVAS", + "isLoading": false, + "maxZoomLevel": 1.0, + "enableDownload": false, + "borderRadius": "0px", + "enableRotation": false + } + ], + "key": "ok1ci5kt2b", + "isDeprecated": false, + "rightColumn": 475.5, + "detachFromLayout": true, + "widgetId": "syjkq3pgjy", + "accentColor": "{{appsmith.theme.colors.primaryColor}}", + "containerStyle": "none", + "isVisible": true, + "version": 1.0, + "parentId": "umf2cog74w", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}" + } + ], + "borderWidth": "1", + "key": "7jawjh2cqc", + "backgroundColor": "#324479", + "isDeprecated": false, + "rightColumn": 14.0, + "dynamicHeight": "FIXED", + "widgetId": "umf2cog74w", + "containerStyle": "card", + "isVisible": true, + "version": 1.0, + "parentId": "0", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "Modal1", + "isCanvas": true, + "displayName": "Modal", + "iconSVG": "/static/media/icon.4975978e.svg", + "topRow": 10.0, + "bottomRow": 34.0, + "parentRowSpace": 10.0, + "type": "MODAL_WIDGET", + "hideCard": false, + "shouldScrollContents": true, + "animateLoading": true, + "parentColumnSpace": 11.3314208984375, + "leftColumn": 20.0, + "dynamicBindingPathList": [], + "children": [ + { + "boxShadow": "none", + "widgetName": "Canvas10", + "displayName": "Canvas", + "topRow": 0.0, + "bottomRow": 770.0, + "parentRowSpace": 1.0, + "type": "CANVAS_WIDGET", + "canExtend": true, + "hideCard": true, + "shouldScrollContents": false, + "minHeight": 778.0, + "parentColumnSpace": 1.0, + "leftColumn": 0.0, + "dynamicBindingPathList": [], + "children": [ + { + "boxShadow": "none", + "widgetName": "Container2CopyCopyCopy", + "borderColor": "", + "isCanvas": true, + "dynamicPropertyPathList": [ + { "key": "borderRadius" } + ], + "displayName": "Container", + "iconSVG": "/static/media/icon.1977dca3.svg", + "topRow": 0.0, + "bottomRow": 74.0, + "parentRowSpace": 10.0, + "type": "CONTAINER_WIDGET", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 18.0625, + "dynamicTriggerPathList": [], + "leftColumn": 0.0, + "dynamicBindingPathList": [], + "children": [ + { + "boxShadow": "none", + "widgetName": "Canvas2CopyCopyCopyCopy", + "displayName": "Canvas", + "topRow": 0.0, + "bottomRow": 730.0, + "parentRowSpace": 1.0, + "type": "CANVAS_WIDGET", + "canExtend": false, + "hideCard": true, + "minHeight": 740.0, + "parentColumnSpace": 1.0, + "leftColumn": 0.0, + "dynamicBindingPathList": [], + "children": [ + { + "boxShadow": "none", + "widgetName": "Button1", + "onClick": "{{update_work_orders1.run(() => select_work_orders.run(), () => {})}}", + "buttonColor": "#2356A1", + "dynamicPropertyPathList": [ + { "key": "onClick" } + ], + "displayName": "Button", + "iconSVG": "/static/media/icon.cca02633.svg", + "topRow": 67.0, + "bottomRow": 72.0, + "parentRowSpace": 10.0, + "type": "BUTTON_WIDGET", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 6.1787109375, + "dynamicTriggerPathList": [ + { "key": "onClick" } + ], + "leftColumn": 44.0, + "dynamicBindingPathList": [], + "text": "Update", + "isDisabled": false, + "key": "fu5cfw8tbj", + "labelTextSize": "0.875rem", + "rightColumn": 63.0, + "isDefaultClickDisabled": true, + "widgetId": "ucz1joszft", + "isVisible": true, + "recaptchaType": "V3", + "version": 1.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0.375rem", + "buttonVariant": "PRIMARY", + "placement": "CENTER" + }, + { + "boxShadow": "none", + "widgetName": "Text2CopyCopyCopyCopyCopyCopy1CopyCopy", + "dynamicPropertyPathList": [ + { "key": "fontSize" } + ], + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b52.svg", + "topRow": 11.0, + "bottomRow": 15.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "dynamicTriggerPathList": [], + "overflow": "NONE", + "fontFamily": "System Default", + "dynamicBindingPathList": [], + "leftColumn": 1.0, + "truncateButtonColor": "#FFC13D", + "text": "Customer Email", + "key": "czyq0gtp0e", + "labelTextSize": "0.875rem", + "rightColumn": 32.0, + "textAlign": "LEFT", + "dynamicHeight": "FIXED", + "widgetId": "bfhd5kcsiq", + "logBlackList": { + "isVisible": true, + "text": true, + "fontSize": true, + "fontStyle": true, + "textAlign": true, + "textColor": true, + "truncateButtonColor": true, + "widgetName": true, + "shouldScroll": true, + "shouldTruncate": true, + "version": true, + "animateLoading": true, + "type": true, + "hideCard": true, + "displayName": true, + "key": true, + "iconSVG": true, + "isCanvas": true, + "textStyle": true, + "dynamicBindingPathList": true, + "dynamicTriggerPathList": true, + "minHeight": true, + "widgetId": true, + "renderMode": true, + "isLoading": true, + "parentColumnSpace": true, + "parentRowSpace": true, + "leftColumn": true, + "rightColumn": true, + "topRow": true, + "bottomRow": true, + "parentId": true + }, + "isVisible": true, + "fontStyle": "", + "textColor": "#231F20", + "version": 1.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "fontSize": "1.125rem", + "textStyle": "HEADING", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "editcustEmail", + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b52.svg", + "topRow": 11.0, + "bottomRow": 15.0, + "parentRowSpace": 10.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "overflow": "NONE", + "parentColumnSpace": 5.6962890625, + "dynamicTriggerPathList": [], + "fontFamily": "System Default", + "leftColumn": 32.0, + "dynamicBindingPathList": [{ "key": "text" }], + "shouldTruncate": false, + "truncateButtonColor": "#FFC13D", + "text": "{{workOrdersTable.triggeredRow.customer_email}}", + "key": "sf3h3c9rxg", + "labelTextSize": "0.875rem", + "rightColumn": 60.0, + "textAlign": "LEFT", + "dynamicHeight": "FIXED", + "widgetId": "6l5jntr587", + "logBlackList": { + "isVisible": true, + "text": true, + "fontSize": true, + "fontStyle": true, + "textAlign": true, + "textColor": true, + "truncateButtonColor": true, + "widgetName": true, + "shouldTruncate": true, + "overflow": true, + "version": true, + "animateLoading": true, + "type": true, + "hideCard": true, + "displayName": true, + "key": true, + "iconSVG": true, + "isCanvas": true, + "minHeight": true, + "widgetId": true, + "renderMode": true, + "isLoading": true, + "parentColumnSpace": true, + "parentRowSpace": true, + "leftColumn": true, + "rightColumn": true, + "topRow": true, + "bottomRow": true, + "parentId": true + }, + "isVisible": true, + "fontStyle": "BOLD", + "textColor": "#231F20", + "version": 1.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "fontSize": "1rem", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "Text2CopyCopyCopyCopyCopyCopy1Copy", + "dynamicPropertyPathList": [ + { "key": "fontSize" } + ], + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b52.svg", + "topRow": 7.0, + "bottomRow": 11.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "dynamicTriggerPathList": [], + "overflow": "NONE", + "fontFamily": "System Default", + "dynamicBindingPathList": [], + "leftColumn": 1.0, + "truncateButtonColor": "#FFC13D", + "text": "Customer Name", + "key": "czyq0gtp0e", + "labelTextSize": "0.875rem", + "rightColumn": 32.0, + "textAlign": "LEFT", + "dynamicHeight": "FIXED", + "widgetId": "k6m249v6fn", + "logBlackList": { + "isVisible": true, + "text": true, + "fontSize": true, + "fontStyle": true, + "textAlign": true, + "textColor": true, + "truncateButtonColor": true, + "widgetName": true, + "shouldScroll": true, + "shouldTruncate": true, + "version": true, + "animateLoading": true, + "type": true, + "hideCard": true, + "displayName": true, + "key": true, + "iconSVG": true, + "isCanvas": true, + "textStyle": true, + "dynamicBindingPathList": true, + "dynamicTriggerPathList": true, + "minHeight": true, + "widgetId": true, + "renderMode": true, + "isLoading": true, + "parentColumnSpace": true, + "parentRowSpace": true, + "leftColumn": true, + "rightColumn": true, + "topRow": true, + "bottomRow": true, + "parentId": true + }, + "isVisible": true, + "fontStyle": "", + "textColor": "#231F20", + "version": 1.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "fontSize": "1.125rem", + "textStyle": "HEADING", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "editcustName", + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b52.svg", + "topRow": 7.0, + "bottomRow": 11.0, + "parentRowSpace": 10.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "overflow": "NONE", + "parentColumnSpace": 5.6962890625, + "dynamicTriggerPathList": [], + "fontFamily": "System Default", + "leftColumn": 32.0, + "dynamicBindingPathList": [{ "key": "text" }], + "shouldTruncate": false, + "truncateButtonColor": "#FFC13D", + "text": "{{workOrdersTable.triggeredRow.customer_name}}", + "key": "sf3h3c9rxg", + "labelTextSize": "0.875rem", + "rightColumn": 60.0, + "textAlign": "LEFT", + "dynamicHeight": "FIXED", + "widgetId": "n5bu6y8d2w", + "logBlackList": { + "isVisible": true, + "text": true, + "fontSize": true, + "fontStyle": true, + "textAlign": true, + "textColor": true, + "truncateButtonColor": true, + "widgetName": true, + "shouldTruncate": true, + "overflow": true, + "version": true, + "animateLoading": true, + "type": true, + "hideCard": true, + "displayName": true, + "key": true, + "iconSVG": true, + "isCanvas": true, + "minHeight": true, + "widgetId": true, + "renderMode": true, + "isLoading": true, + "parentColumnSpace": true, + "parentRowSpace": true, + "leftColumn": true, + "rightColumn": true, + "topRow": true, + "bottomRow": true, + "parentId": true + }, + "isVisible": true, + "fontStyle": "BOLD", + "textColor": "#231F20", + "version": 1.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "fontSize": "1rem", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "editCompleted", + "isFilterable": true, + "displayName": "Select", + "iconSVG": "/static/media/icon.bd99caba.svg", + "labelText": "", + "topRow": 49.0, + "bottomRow": 53.0, + "parentRowSpace": 10.0, + "type": "SELECT_WIDGET", + "serverSideFiltering": false, + "hideCard": false, + "defaultOptionValue": "{{ ((options, serverSideFiltering) => ( workOrdersTable.triggeredRow.completed|| ''))(editCompleted.options, editCompleted.serverSideFiltering) }}", + "animateLoading": true, + "parentColumnSpace": 5.853515625, + "dynamicTriggerPathList": [], + "leftColumn": 33.0, + "dynamicBindingPathList": [ + { "key": "defaultOptionValue" }, + { "key": "accentColor" } + ], + "placeholderText": "Select option", + "isDisabled": false, + "key": "o6darbc32i", + "labelTextSize": "0.875rem", + "isRequired": false, + "rightColumn": 63.0, + "dynamicHeight": "FIXED", + "widgetId": "26sfdw8ffd", + "accentColor": "{{appsmith.theme.colors.primaryColor}}", + "isVisible": true, + "version": 1.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "minDynamicHeight": 4.0, + "sourceData": "[\n {\n \"label\": \"Yes\",\n \"value\": \"Yes\"\n },\n {\n \"label\": \"No\",\n \"value\": \"No\"\n }\n]", + "optionLabel": "label", + "optionValue": "value", + "dynamicPropertyPathList": [ + { "key": "sourceData" } + ] + }, + { + "boxShadow": "none", + "widgetName": "editHoursUsed", + "displayName": "Input", + "iconSVG": "/static/media/icon.9f505595.svg", + "topRow": 53.0, + "bottomRow": 57.0, + "parentRowSpace": 10.0, + "autoFocus": false, + "type": "INPUT_WIDGET_V2", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 5.853515625, + "dynamicTriggerPathList": [], + "resetOnSubmit": true, + "leftColumn": 33.0, + "dynamicBindingPathList": [ + { "key": "defaultText" }, + { "key": "accentColor" } + ], + "labelStyle": "", + "inputType": "NUMBER", + "isDisabled": false, + "key": "frh9e8lhpg", + "labelTextSize": "0.875rem", + "isRequired": false, + "rightColumn": 63.0, + "dynamicHeight": "FIXED", + "widgetId": "6e5isq741m", + "accentColor": "{{appsmith.theme.colors.primaryColor}}", + "showStepArrows": true, + "isVisible": true, + "label": "", + "version": 2.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "iconAlign": "left", + "defaultText": "{{workOrdersTable.triggeredRow.hours || ''}}", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "editMC", + "displayName": "Currency Input", + "iconSVG": "/static/media/icon.f312efcb.svg", + "topRow": 57.0, + "bottomRow": 61.0, + "defaultCurrencyCode": "USD", + "parentRowSpace": 10.0, + "autoFocus": false, + "type": "CURRENCY_INPUT_WIDGET", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 5.853515625, + "dynamicTriggerPathList": [], + "resetOnSubmit": true, + "leftColumn": 33.0, + "dynamicBindingPathList": [ + { "key": "defaultText" }, + { "key": "accentColor" } + ], + "labelPosition": "Left", + "labelStyle": "", + "isDisabled": false, + "key": "3g9dnqeeie", + "labelTextSize": "0.875rem", + "isRequired": false, + "rightColumn": 63.0, + "dynamicHeight": "FIXED", + "widgetId": "k59tc507ay", + "accentColor": "{{appsmith.theme.colors.primaryColor}}", + "showStepArrows": true, + "isVisible": true, + "label": "", + "allowCurrencyChange": false, + "version": 1.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "decimals": 0.0, + "iconAlign": "left", + "defaultText": "{{\nworkOrdersTable.triggeredRow.mat_cost ? workOrdersTable.triggeredRow.mat_cost : 0}}", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "editTC", + "displayName": "Currency Input", + "iconSVG": "/static/media/icon.f312efcb.svg", + "topRow": 61.0, + "bottomRow": 65.0, + "defaultCurrencyCode": "USD", + "parentRowSpace": 10.0, + "autoFocus": false, + "type": "CURRENCY_INPUT_WIDGET", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 5.853515625, + "dynamicTriggerPathList": [], + "resetOnSubmit": true, + "leftColumn": 33.0, + "dynamicBindingPathList": [ + { "key": "defaultText" }, + { "key": "accentColor" } + ], + "labelPosition": "Left", + "labelStyle": "", + "isDisabled": false, + "key": "3g9dnqeeie", + "labelTextSize": "0.875rem", + "isRequired": false, + "rightColumn": 63.0, + "dynamicHeight": "FIXED", + "widgetId": "09gy1q8fof", + "accentColor": "{{appsmith.theme.colors.primaryColor}}", + "showStepArrows": true, + "isVisible": true, + "label": "", + "allowCurrencyChange": false, + "version": 1.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "decimals": 0.0, + "iconAlign": "left", + "defaultText": "{{\nworkOrdersTable.triggeredRow.total_cost ? workOrdersTable.triggeredRow.total_cost : 0}}", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "editEquipment", + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b52.svg", + "topRow": 15.0, + "bottomRow": 19.0, + "parentRowSpace": 10.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "overflow": "NONE", + "parentColumnSpace": 5.6962890625, + "dynamicTriggerPathList": [], + "fontFamily": "System Default", + "leftColumn": 32.0, + "dynamicBindingPathList": [{ "key": "text" }], + "shouldTruncate": false, + "truncateButtonColor": "#FFC13D", + "text": "{{workOrdersTable.triggeredRow.equipment}}", + "key": "sf3h3c9rxg", + "labelTextSize": "0.875rem", + "rightColumn": 48.0, + "textAlign": "LEFT", + "dynamicHeight": "FIXED", + "widgetId": "2tpeti2iys", + "logBlackList": { + "isVisible": true, + "text": true, + "fontSize": true, + "fontStyle": true, + "textAlign": true, + "textColor": true, + "truncateButtonColor": true, + "widgetName": true, + "shouldTruncate": true, + "overflow": true, + "version": true, + "animateLoading": true, + "type": true, + "hideCard": true, + "displayName": true, + "key": true, + "iconSVG": true, + "isCanvas": true, + "minHeight": true, + "widgetId": true, + "renderMode": true, + "isLoading": true, + "parentColumnSpace": true, + "parentRowSpace": true, + "leftColumn": true, + "rightColumn": true, + "topRow": true, + "bottomRow": true, + "parentId": true + }, + "isVisible": true, + "fontStyle": "BOLD", + "textColor": "#231F20", + "version": 1.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "fontSize": "1rem", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "editorderCategory", + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b52.svg", + "topRow": 19.0, + "bottomRow": 23.0, + "parentRowSpace": 10.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "overflow": "NONE", + "parentColumnSpace": 5.6962890625, + "dynamicTriggerPathList": [], + "fontFamily": "System Default", + "leftColumn": 32.0, + "dynamicBindingPathList": [{ "key": "text" }], + "shouldTruncate": false, + "truncateButtonColor": "#FFC13D", + "text": "{{workOrdersTable.triggeredRow.category}}", + "key": "sf3h3c9rxg", + "labelTextSize": "0.875rem", + "rightColumn": 64.0, + "textAlign": "LEFT", + "dynamicHeight": "FIXED", + "widgetId": "kxgtej06ta", + "logBlackList": { + "isVisible": true, + "text": true, + "fontSize": true, + "fontStyle": true, + "textAlign": true, + "textColor": true, + "truncateButtonColor": true, + "widgetName": true, + "shouldTruncate": true, + "overflow": true, + "version": true, + "animateLoading": true, + "type": true, + "hideCard": true, + "displayName": true, + "key": true, + "iconSVG": true, + "isCanvas": true, + "minHeight": true, + "widgetId": true, + "renderMode": true, + "isLoading": true, + "parentColumnSpace": true, + "parentRowSpace": true, + "leftColumn": true, + "rightColumn": true, + "topRow": true, + "bottomRow": true, + "parentId": true + }, + "isVisible": true, + "fontStyle": "BOLD", + "textColor": "#231F20", + "version": 1.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "fontSize": "1rem", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "editorderDesc", + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b52.svg", + "topRow": 23.0, + "bottomRow": 27.0, + "parentRowSpace": 10.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "overflow": "TRUNCATE", + "parentColumnSpace": 5.6962890625, + "dynamicTriggerPathList": [], + "fontFamily": "System Default", + "leftColumn": 32.0, + "dynamicBindingPathList": [{ "key": "text" }], + "shouldTruncate": false, + "truncateButtonColor": "#FFC13D", + "text": "{{workOrdersTable.triggeredRow.description}}", + "key": "sf3h3c9rxg", + "labelTextSize": "0.875rem", + "rightColumn": 64.0, + "textAlign": "LEFT", + "dynamicHeight": "FIXED", + "widgetId": "mp159xsz1c", + "logBlackList": { + "isVisible": true, + "text": true, + "fontSize": true, + "fontStyle": true, + "textAlign": true, + "textColor": true, + "truncateButtonColor": true, + "widgetName": true, + "shouldTruncate": true, + "overflow": true, + "version": true, + "animateLoading": true, + "type": true, + "hideCard": true, + "displayName": true, + "key": true, + "iconSVG": true, + "isCanvas": true, + "minHeight": true, + "widgetId": true, + "renderMode": true, + "isLoading": true, + "parentColumnSpace": true, + "parentRowSpace": true, + "leftColumn": true, + "rightColumn": true, + "topRow": true, + "bottomRow": true, + "parentId": true + }, + "isVisible": true, + "fontStyle": "BOLD", + "textColor": "#231F20", + "version": 1.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "fontSize": "1rem", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "Text2CopyCopyCopy1CopyCopyCopyCopy", + "dynamicPropertyPathList": [ + { "key": "fontSize" } + ], + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b52.svg", + "topRow": 57.0, + "bottomRow": 61.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "dynamicTriggerPathList": [], + "overflow": "NONE", + "fontFamily": "System Default", + "dynamicBindingPathList": [], + "leftColumn": 1.0, + "truncateButtonColor": "#FFC13D", + "text": "Material costs", + "key": "czyq0gtp0e", + "labelTextSize": "0.875rem", + "rightColumn": 32.0, + "textAlign": "LEFT", + "dynamicHeight": "FIXED", + "widgetId": "7vj1eoncah", + "logBlackList": { + "isVisible": true, + "text": true, + "fontSize": true, + "fontStyle": true, + "textAlign": true, + "textColor": true, + "truncateButtonColor": true, + "widgetName": true, + "shouldScroll": true, + "shouldTruncate": true, + "version": true, + "animateLoading": true, + "type": true, + "hideCard": true, + "displayName": true, + "key": true, + "iconSVG": true, + "isCanvas": true, + "textStyle": true, + "dynamicBindingPathList": true, + "dynamicTriggerPathList": true, + "minHeight": true, + "widgetId": true, + "renderMode": true, + "isLoading": true, + "parentColumnSpace": true, + "parentRowSpace": true, + "leftColumn": true, + "rightColumn": true, + "topRow": true, + "bottomRow": true, + "parentId": true + }, + "isVisible": true, + "fontStyle": "", + "textColor": "#231F20", + "version": 1.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "fontSize": "1.125rem", + "textStyle": "HEADING", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "Text2CopyCopyCopyCopyCopyCopyCopyCopy", + "dynamicPropertyPathList": [ + { "key": "fontSize" } + ], + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b52.svg", + "topRow": 61.0, + "bottomRow": 65.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "dynamicTriggerPathList": [], + "overflow": "NONE", + "fontFamily": "System Default", + "dynamicBindingPathList": [], + "leftColumn": 1.0, + "truncateButtonColor": "#FFC13D", + "text": "Total costs", + "key": "czyq0gtp0e", + "labelTextSize": "0.875rem", + "rightColumn": 32.0, + "textAlign": "LEFT", + "dynamicHeight": "FIXED", + "widgetId": "9qfaoghg82", + "logBlackList": { + "isVisible": true, + "text": true, + "fontSize": true, + "fontStyle": true, + "textAlign": true, + "textColor": true, + "truncateButtonColor": true, + "widgetName": true, + "shouldScroll": true, + "shouldTruncate": true, + "version": true, + "animateLoading": true, + "type": true, + "hideCard": true, + "displayName": true, + "key": true, + "iconSVG": true, + "isCanvas": true, + "textStyle": true, + "dynamicBindingPathList": true, + "dynamicTriggerPathList": true, + "minHeight": true, + "widgetId": true, + "renderMode": true, + "isLoading": true, + "parentColumnSpace": true, + "parentRowSpace": true, + "leftColumn": true, + "rightColumn": true, + "topRow": true, + "bottomRow": true, + "parentId": true + }, + "isVisible": true, + "fontStyle": "", + "textColor": "#231F20", + "version": 1.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "fontSize": "1.125rem", + "textStyle": "HEADING", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "Text2CopyCopyCopy2CopyCopy", + "dynamicPropertyPathList": [ + { "key": "fontSize" } + ], + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b52.svg", + "topRow": 31.0, + "bottomRow": 35.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "dynamicTriggerPathList": [], + "overflow": "NONE", + "fontFamily": "System Default", + "dynamicBindingPathList": [], + "leftColumn": 1.0, + "truncateButtonColor": "#FFC13D", + "text": "Agent", + "key": "czyq0gtp0e", + "labelTextSize": "0.875rem", + "rightColumn": 32.0, + "textAlign": "LEFT", + "dynamicHeight": "FIXED", + "widgetId": "790vfcz8wc", + "logBlackList": { + "isVisible": true, + "text": true, + "fontSize": true, + "fontStyle": true, + "textAlign": true, + "textColor": true, + "truncateButtonColor": true, + "widgetName": true, + "shouldScroll": true, + "shouldTruncate": true, + "version": true, + "animateLoading": true, + "type": true, + "hideCard": true, + "displayName": true, + "key": true, + "iconSVG": true, + "isCanvas": true, + "textStyle": true, + "dynamicBindingPathList": true, + "dynamicTriggerPathList": true, + "minHeight": true, + "widgetId": true, + "renderMode": true, + "isLoading": true, + "parentColumnSpace": true, + "parentRowSpace": true, + "leftColumn": true, + "rightColumn": true, + "topRow": true, + "bottomRow": true, + "parentId": true + }, + "isVisible": true, + "fontStyle": "", + "textColor": "#231F20", + "version": 1.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "fontSize": "1.125rem", + "textStyle": "HEADING", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "Text2CopyCopyCopyCopy1CopyCopy", + "dynamicPropertyPathList": [ + { "key": "fontSize" } + ], + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b52.svg", + "topRow": 35.0, + "bottomRow": 39.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "dynamicTriggerPathList": [], + "overflow": "NONE", + "fontFamily": "System Default", + "dynamicBindingPathList": [], + "leftColumn": 1.0, + "truncateButtonColor": "#FFC13D", + "text": "Maintenance Notes", + "key": "czyq0gtp0e", + "labelTextSize": "0.875rem", + "rightColumn": 32.0, + "textAlign": "LEFT", + "dynamicHeight": "FIXED", + "widgetId": "lv643q4grv", + "logBlackList": { + "isVisible": true, + "text": true, + "fontSize": true, + "fontStyle": true, + "textAlign": true, + "textColor": true, + "truncateButtonColor": true, + "widgetName": true, + "shouldScroll": true, + "shouldTruncate": true, + "version": true, + "animateLoading": true, + "type": true, + "hideCard": true, + "displayName": true, + "key": true, + "iconSVG": true, + "isCanvas": true, + "textStyle": true, + "dynamicBindingPathList": true, + "dynamicTriggerPathList": true, + "minHeight": true, + "widgetId": true, + "renderMode": true, + "isLoading": true, + "parentColumnSpace": true, + "parentRowSpace": true, + "leftColumn": true, + "rightColumn": true, + "topRow": true, + "bottomRow": true, + "parentId": true + }, + "isVisible": true, + "fontStyle": "", + "textColor": "#231F20", + "version": 1.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "fontSize": "1.125rem", + "textStyle": "HEADING", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "Text2CopyCopyCopy1CopyCopyCopy1", + "dynamicPropertyPathList": [ + { "key": "fontSize" } + ], + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b52.svg", + "topRow": 49.0, + "bottomRow": 53.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "dynamicTriggerPathList": [], + "overflow": "NONE", + "fontFamily": "System Default", + "dynamicBindingPathList": [], + "leftColumn": 1.0, + "truncateButtonColor": "#FFC13D", + "text": "Completed", + "key": "czyq0gtp0e", + "labelTextSize": "0.875rem", + "rightColumn": 32.0, + "textAlign": "LEFT", + "dynamicHeight": "FIXED", + "widgetId": "365wjz96s9", + "logBlackList": { + "isVisible": true, + "text": true, + "fontSize": true, + "fontStyle": true, + "textAlign": true, + "textColor": true, + "truncateButtonColor": true, + "widgetName": true, + "shouldScroll": true, + "shouldTruncate": true, + "version": true, + "animateLoading": true, + "type": true, + "hideCard": true, + "displayName": true, + "key": true, + "iconSVG": true, + "isCanvas": true, + "textStyle": true, + "dynamicBindingPathList": true, + "dynamicTriggerPathList": true, + "minHeight": true, + "widgetId": true, + "renderMode": true, + "isLoading": true, + "parentColumnSpace": true, + "parentRowSpace": true, + "leftColumn": true, + "rightColumn": true, + "topRow": true, + "bottomRow": true, + "parentId": true + }, + "isVisible": true, + "fontStyle": "", + "textColor": "#231F20", + "version": 1.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "fontSize": "1.125rem", + "textStyle": "HEADING", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "Text2CopyCopyCopyCopyCopyCopyCopy1", + "dynamicPropertyPathList": [ + { "key": "fontSize" } + ], + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b52.svg", + "topRow": 53.0, + "bottomRow": 57.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "dynamicTriggerPathList": [], + "overflow": "NONE", + "fontFamily": "System Default", + "dynamicBindingPathList": [], + "leftColumn": 1.0, + "truncateButtonColor": "#FFC13D", + "text": "Hours used", + "key": "czyq0gtp0e", + "labelTextSize": "0.875rem", + "rightColumn": 32.0, + "textAlign": "LEFT", + "dynamicHeight": "FIXED", + "widgetId": "kqp5yxv9q7", + "logBlackList": { + "isVisible": true, + "text": true, + "fontSize": true, + "fontStyle": true, + "textAlign": true, + "textColor": true, + "truncateButtonColor": true, + "widgetName": true, + "shouldScroll": true, + "shouldTruncate": true, + "version": true, + "animateLoading": true, + "type": true, + "hideCard": true, + "displayName": true, + "key": true, + "iconSVG": true, + "isCanvas": true, + "textStyle": true, + "dynamicBindingPathList": true, + "dynamicTriggerPathList": true, + "minHeight": true, + "widgetId": true, + "renderMode": true, + "isLoading": true, + "parentColumnSpace": true, + "parentRowSpace": true, + "leftColumn": true, + "rightColumn": true, + "topRow": true, + "bottomRow": true, + "parentId": true + }, + "isVisible": true, + "fontStyle": "", + "textColor": "#231F20", + "version": 1.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "fontSize": "1.125rem", + "textStyle": "HEADING", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "Text2CopyCopyCopy2Copy1", + "dynamicPropertyPathList": [ + { "key": "fontSize" } + ], + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b52.svg", + "topRow": 15.0, + "bottomRow": 19.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "dynamicTriggerPathList": [], + "overflow": "NONE", + "fontFamily": "System Default", + "dynamicBindingPathList": [], + "leftColumn": 1.0, + "truncateButtonColor": "#FFC13D", + "text": "Equipment", + "key": "czyq0gtp0e", + "labelTextSize": "0.875rem", + "rightColumn": 32.0, + "textAlign": "LEFT", + "dynamicHeight": "FIXED", + "widgetId": "u5bsq2tcyh", + "logBlackList": { + "isVisible": true, + "text": true, + "fontSize": true, + "fontStyle": true, + "textAlign": true, + "textColor": true, + "truncateButtonColor": true, + "widgetName": true, + "shouldScroll": true, + "shouldTruncate": true, + "version": true, + "animateLoading": true, + "type": true, + "hideCard": true, + "displayName": true, + "key": true, + "iconSVG": true, + "isCanvas": true, + "textStyle": true, + "dynamicBindingPathList": true, + "dynamicTriggerPathList": true, + "minHeight": true, + "widgetId": true, + "renderMode": true, + "isLoading": true, + "parentColumnSpace": true, + "parentRowSpace": true, + "leftColumn": true, + "rightColumn": true, + "topRow": true, + "bottomRow": true, + "parentId": true + }, + "isVisible": true, + "fontStyle": "", + "textColor": "#231F20", + "version": 1.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "fontSize": "1.125rem", + "textStyle": "HEADING", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "Text2CopyCopyCopyCopy1Copy1", + "dynamicPropertyPathList": [ + { "key": "fontSize" } + ], + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b52.svg", + "topRow": 19.0, + "bottomRow": 23.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "dynamicTriggerPathList": [], + "overflow": "NONE", + "fontFamily": "System Default", + "dynamicBindingPathList": [], + "leftColumn": 1.0, + "truncateButtonColor": "#FFC13D", + "text": "Category", + "key": "czyq0gtp0e", + "labelTextSize": "0.875rem", + "rightColumn": 32.0, + "textAlign": "LEFT", + "dynamicHeight": "FIXED", + "widgetId": "5elxnkbnz3", + "logBlackList": { + "isVisible": true, + "text": true, + "fontSize": true, + "fontStyle": true, + "textAlign": true, + "textColor": true, + "truncateButtonColor": true, + "widgetName": true, + "shouldScroll": true, + "shouldTruncate": true, + "version": true, + "animateLoading": true, + "type": true, + "hideCard": true, + "displayName": true, + "key": true, + "iconSVG": true, + "isCanvas": true, + "textStyle": true, + "dynamicBindingPathList": true, + "dynamicTriggerPathList": true, + "minHeight": true, + "widgetId": true, + "renderMode": true, + "isLoading": true, + "parentColumnSpace": true, + "parentRowSpace": true, + "leftColumn": true, + "rightColumn": true, + "topRow": true, + "bottomRow": true, + "parentId": true + }, + "isVisible": true, + "fontStyle": "", + "textColor": "#231F20", + "version": 1.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "fontSize": "1.125rem", + "textStyle": "HEADING", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "Text2CopyCopyCopy1CopyCopy1", + "dynamicPropertyPathList": [ + { "key": "fontSize" } + ], + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b52.svg", + "topRow": 23.0, + "bottomRow": 27.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "dynamicTriggerPathList": [], + "overflow": "NONE", + "fontFamily": "System Default", + "dynamicBindingPathList": [], + "leftColumn": 1.0, + "truncateButtonColor": "#FFC13D", + "text": "Description", + "key": "czyq0gtp0e", + "labelTextSize": "0.875rem", + "rightColumn": 32.0, + "textAlign": "LEFT", + "dynamicHeight": "FIXED", + "widgetId": "9nbm9qanpb", + "logBlackList": { + "isVisible": true, + "text": true, + "fontSize": true, + "fontStyle": true, + "textAlign": true, + "textColor": true, + "truncateButtonColor": true, + "widgetName": true, + "shouldScroll": true, + "shouldTruncate": true, + "version": true, + "animateLoading": true, + "type": true, + "hideCard": true, + "displayName": true, + "key": true, + "iconSVG": true, + "isCanvas": true, + "textStyle": true, + "dynamicBindingPathList": true, + "dynamicTriggerPathList": true, + "minHeight": true, + "widgetId": true, + "renderMode": true, + "isLoading": true, + "parentColumnSpace": true, + "parentRowSpace": true, + "leftColumn": true, + "rightColumn": true, + "topRow": true, + "bottomRow": true, + "parentId": true + }, + "isVisible": true, + "fontStyle": "", + "textColor": "#231F20", + "version": 1.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "fontSize": "1.125rem", + "textStyle": "HEADING", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "Text2CopyCopyCopyCopyCopyCopy1", + "dynamicPropertyPathList": [ + { "key": "fontSize" } + ], + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b52.svg", + "topRow": 27.0, + "bottomRow": 31.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "dynamicTriggerPathList": [], + "overflow": "NONE", + "fontFamily": "System Default", + "dynamicBindingPathList": [], + "leftColumn": 1.0, + "truncateButtonColor": "#FFC13D", + "text": "Requested Date", + "key": "czyq0gtp0e", + "labelTextSize": "0.875rem", + "rightColumn": 32.0, + "textAlign": "LEFT", + "dynamicHeight": "FIXED", + "widgetId": "x3pmvgu1ei", + "logBlackList": { + "isVisible": true, + "text": true, + "fontSize": true, + "fontStyle": true, + "textAlign": true, + "textColor": true, + "truncateButtonColor": true, + "widgetName": true, + "shouldScroll": true, + "shouldTruncate": true, + "version": true, + "animateLoading": true, + "type": true, + "hideCard": true, + "displayName": true, + "key": true, + "iconSVG": true, + "isCanvas": true, + "textStyle": true, + "dynamicBindingPathList": true, + "dynamicTriggerPathList": true, + "minHeight": true, + "widgetId": true, + "renderMode": true, + "isLoading": true, + "parentColumnSpace": true, + "parentRowSpace": true, + "leftColumn": true, + "rightColumn": true, + "topRow": true, + "bottomRow": true, + "parentId": true + }, + "isVisible": true, + "fontStyle": "", + "textColor": "#231F20", + "version": 1.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "fontSize": "1.125rem", + "textStyle": "HEADING", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "Text4CopyCopyCopyCopy", + "dynamicPropertyPathList": [ + { "key": "fontSize" } + ], + "displayName": "Text", + "iconSVG": "/static/media/icon.97c59b52.svg", + "topRow": 0.0, + "bottomRow": 4.0, + "parentRowSpace": 10.0, + "type": "TEXT_WIDGET", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 10.1298828125, + "dynamicTriggerPathList": [], + "overflow": "NONE", + "fontFamily": "System Default", + "leftColumn": 1.0, + "dynamicBindingPathList": [{ "key": "text" }], + "truncateButtonColor": "#FFC13D", + "text": "Work Order ID: {{workOrdersTable.triggeredRow.work_id}}", + "key": "czyq0gtp0e", + "labelTextSize": "0.875rem", + "rightColumn": 40.0, + "textAlign": "LEFT", + "dynamicHeight": "FIXED", + "widgetId": "lk7gi111se", + "isVisible": true, + "fontStyle": "BOLD", + "textColor": "#231F20", + "version": 1.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "fontSize": "1.5rem", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "editRequestedDate", + "minDate": "1920-12-31T18:30:00.000Z", + "dateFormat": "YYYY-MM-DD", + "dynamicPropertyPathList": [ + { "key": "defaultDate" } + ], + "displayName": "DatePicker", + "iconSVG": "/static/media/icon.300e5ab8.svg", + "topRow": 27.0, + "bottomRow": 31.0, + "shortcuts": false, + "parentRowSpace": 10.0, + "type": "DATE_PICKER_WIDGET2", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 5.853515625, + "dynamicTriggerPathList": [], + "leftColumn": 32.0, + "dynamicBindingPathList": [ + { "key": "defaultDate" }, + { "key": "accentColor" } + ], + "isDisabled": false, + "key": "g6ypr5b6bx", + "labelTextSize": "1rem", + "isRequired": false, + "rightColumn": 53.0, + "defaultDate": "{{\nworkOrdersTable.triggeredRow.request_date ? \nmoment(workOrdersTable.triggeredRow.request_date, \"YYYY-MM-DD\") : new Date().toISOString() }}", + "dynamicHeight": "FIXED", + "widgetId": "ougwj8lmur", + "accentColor": "{{appsmith.theme.colors.primaryColor}}", + "isVisible": true, + "datePickerType": "DATE_PICKER", + "label": "", + "version": 2.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "timePrecision": "None", + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "firstDayOfWeek": 0.0, + "closeOnSelection": true, + "maxDate": "2121-12-31T18:29:00.000Z", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "IconButton3", + "onClick": "{{closeModal('Modal1')}}", + "buttonColor": "#2E3D49", + "displayName": "Icon Button", + "iconSVG": "/static/media/icon.1a0c634a.svg", + "topRow": 0.0, + "bottomRow": 4.0, + "type": "ICON_BUTTON_WIDGET", + "hideCard": false, + "animateLoading": true, + "leftColumn": 55.0, + "dynamicBindingPathList": [], + "iconSize": 24.0, + "isDisabled": false, + "key": "he5p9ovxh4", + "labelTextSize": "0.875rem", + "rightColumn": 63.0, + "iconName": "cross", + "widgetId": "c5tlnajq5j", + "isVisible": true, + "version": 1.0, + "parentId": "cryduleyoi", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "buttonVariant": "TERTIARY" + }, + { + "boxShadow": "none", + "widgetName": "editNotes", + "displayName": "Input", + "iconSVG": "/static/media/icon.9f505595.svg", + "topRow": 39.0, + "bottomRow": 49.0, + "parentRowSpace": 10.0, + "labelWidth": 5.0, + "autoFocus": false, + "type": "INPUT_WIDGET_V2", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 7.193359375, + "dynamicTriggerPathList": [], + "resetOnSubmit": true, + "leftColumn": 1.0, + "dynamicBindingPathList": [ + { "key": "defaultText" }, + { "key": "accentColor" } + ], + "labelPosition": "Left", + "labelStyle": "", + "inputType": "MULTI_LINE_TEXT", + "isDisabled": false, + "key": "8caqtpfmrx", + "labelTextSize": "0.875rem", + "isRequired": false, + "rightColumn": 62.0, + "dynamicHeight": "FIXED", + "widgetId": "oixrmpekwv", + "accentColor": "{{appsmith.theme.colors.primaryColor}}", + "isVisible": true, + "label": "", + "version": 2.0, + "parentId": "cryduleyoi", + "labelAlignment": "left", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "iconAlign": "left", + "defaultText": "{{workOrdersTable.triggeredRow.maintenance_notes}}", + "minDynamicHeight": 4.0 + }, + { + "boxShadow": "none", + "widgetName": "editOrderAgent", + "isFilterable": true, + "dynamicPropertyPathList": [ + { "key": "sourceData" } + ], + "displayName": "Select", + "iconSVG": "/static/media/icon.bd99caba.svg", + "labelText": "", + "topRow": 31.0, + "bottomRow": 35.0, + "parentRowSpace": 10.0, + "labelWidth": 5.0, + "type": "SELECT_WIDGET", + "serverSideFiltering": false, + "hideCard": false, + "defaultOptionValue": "{{ ((options, serverSideFiltering) => ( workOrdersTable.triggeredRow.agent || ''))(editOrderAgent.options, editOrderAgent.serverSideFiltering) }}", + "animateLoading": true, + "parentColumnSpace": 7.193359375, + "dynamicTriggerPathList": [ + { "key": "onOptionChange" } + ], + "leftColumn": 32.0, + "dynamicBindingPathList": [ + { "key": "options" }, + { "key": "defaultOptionValue" }, + { "key": "accentColor" } + ], + "labelPosition": "Left", + "placeholderText": "Select option", + "isDisabled": false, + "key": "vpduhjc9fo", + "labelTextSize": "1rem", + "isRequired": false, + "rightColumn": 64.0, + "dynamicHeight": "FIXED", + "widgetId": "n1di761cbl", + "accentColor": "{{appsmith.theme.colors.primaryColor}}", + "isVisible": true, + "version": 1.0, + "parentId": "cryduleyoi", + "labelAlignment": "left", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "onOptionChange": "", + "minDynamicHeight": 4.0, + "sourceData": "[\n {\n \"label\": {{select_agent.data[0].agent}},\n \"value\": {{select_agent.data[0].agent}}\n },\n\t {\n \"label\": {{select_agent.data[2].agent}},\n \"value\": {{select_agent.data[2].agent}}\n },\n\t {\n \"label\": {{select_agent.data[3].agent}},\n \"value\": {{select_agent.data[3].agent}}\n },\n\t {\n \"label\": {{select_agent.data[4].agent}},\n \"value\": {{select_agent.data[4].agent}}\n },\n\t {\n \"label\": {{select_agent.data[1].agent}},\n \"value\": {{select_agent.data[1].agent}}\n }\n]", + "optionLabel": "label", + "optionValue": "value" + } + ], + "key": "ffadum178l", + "labelTextSize": "0.875rem", + "rightColumn": 433.5, + "detachFromLayout": true, + "widgetId": "cryduleyoi", + "containerStyle": "none", + "isVisible": true, + "version": 1.0, + "parentId": "oyphk6wrsq", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px" + } + ], + "borderWidth": "2", + "key": "6bzu8mpizb", + "labelTextSize": "0.875rem", + "backgroundColor": "#FFFFFF", + "rightColumn": 63.0, + "dynamicHeight": "FIXED", + "widgetId": "oyphk6wrsq", + "containerStyle": "card", + "isVisible": true, + "version": 1.0, + "parentId": "tewt2qrngx", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "15px", + "maxDynamicHeight": 9000.0, + "minDynamicHeight": 4.0 + } + ], + "isDisabled": false, + "key": "b8t0kybjms", + "labelTextSize": "0.875rem", + "rightColumn": 271.9541015625, + "detachFromLayout": true, + "widgetId": "tewt2qrngx", + "isVisible": true, + "version": 1.0, + "parentId": "77pbwrchpt", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px" + } + ], + "key": "ykhy01l1u0", + "height": 778.0, + "labelTextSize": "0.875rem", + "rightColumn": 44.0, + "detachFromLayout": true, + "dynamicHeight": "FIXED", + "widgetId": "77pbwrchpt", + "canOutsideClickClose": true, + "canEscapeKeyClose": true, + "version": 2.0, + "parentId": "0", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "0px", + "maxDynamicHeight": 9000.0, + "width": 684.0, + "minDynamicHeight": 4.0 + }, + { + "setAdaptiveYMin": false, + "boxShadow": "none", + "widgetName": "equipmentPieChart", + "allowScroll": false, + "dynamicPropertyPathList": [{ "key": "isVisible" }], + "displayName": "Chart", + "iconSVG": "/static/media/icon.6adbe31e.svg", + "topRow": 10.0, + "bottomRow": 42.0, + "parentRowSpace": 10.0, + "type": "CHART_WIDGET", + "hideCard": false, + "chartData": { + "ofl8b3apgp": { + "seriesName": "", + "data": "{{appsmith.store.equipmentStats ? appsmith.store.equipmentStats : [] }}" + } + }, + "animateLoading": true, + "parentColumnSpace": 11.70703125, + "dynamicTriggerPathList": [], + "fontFamily": "{{appsmith.theme.fontFamily.appFont}}", + "leftColumn": 31.0, + "dynamicBindingPathList": [ + { "key": "chartData.ofl8b3apgp.data" } + ], + "customFusionChartConfig": { + "type": "column2d", + "dataSource": { + "chart": { + "caption": "Sales Report", + "xAxisName": "Product Line", + "yAxisName": "Revenue($)", + "theme": "fusion" + }, + "data": [ + { "label": "Product1", "value": 20000.0 }, + { "label": "Product2", "value": 22000.0 }, + { "label": "Product3", "value": 32000.0 } + ] + } + }, + "key": "yzaa8q6whh", + "labelTextSize": "0.875rem", + "rightColumn": 63.0, + "widgetId": "v0qy4koas9", + "accentColor": "{{appsmith.theme.colors.primaryColor}}", + "isVisible": "true", + "version": 1.0, + "parentId": "0", + "labelOrientation": "auto", + "renderMode": "CANVAS", + "isLoading": false, + "yAxisName": "", + "chartName": "Equipment", + "borderRadius": "0px", + "xAxisName": "", + "chartType": "PIE_CHART", + "showDataPointLabel": false, + "customEChartConfig": { + "dataset": { + "source": [ + ["Day", "Baidu", "Google", "Bing"], + ["Mon", 620.0, 120.0, 60.0], + ["Tue", 732.0, 132.0, 72.0], + ["Wed", 701.0, 101.0, 71.0], + ["Thu", 734.0, 134.0, 74.0], + ["Fri", 1090.0, 290.0, 190.0], + ["Sat", 1130.0, 230.0, 130.0], + ["Sun", 1120.0, 220.0, 110.0] + ] + }, + "tooltip": { + "trigger": "axis", + "axisPointer": { "type": "shadow" } + }, + "title": { + "text": "Search Engine Usage", + "left": "center", + "textStyle": { "width": 200.0, "overflow": "truncate" } + }, + "legend": { "top": 40.0, "type": "scroll" }, + "grid": { + "left": 15.0, + "right": 15.0, + "bottom": 30.0, + "top": 100.0, + "containLabel": true + }, + "xAxis": [{ "type": "category" }], + "yAxis": [{ "type": "value" }], + "series": [ + { "type": "bar", "stack": "Search Engine" }, + { "type": "bar", "stack": "Search Engine" }, + { "type": "bar", "stack": "Search Engine" } + ] + } + }, + { + "boxShadow": "none", + "widgetName": "IconButton4", + "buttonColor": "{{appsmith.theme.colors.primaryColor}}", + "displayName": "Icon Button", + "iconSVG": "/static/media/icon.1a0c634ac75f9fa6b6ae7a8df882a3ba.svg", + "searchTags": ["click", "submit"], + "topRow": 46.0, + "bottomRow": 50.0, + "parentRowSpace": 10.0, + "type": "ICON_BUTTON_WIDGET", + "hideCard": false, + "animateLoading": true, + "parentColumnSpace": 19.8125, + "dynamicTriggerPathList": [], + "leftColumn": 15.0, + "dynamicBindingPathList": [ + { "key": "buttonColor" }, + { "key": "borderRadius" } + ], + "isDisabled": false, + "key": "qyezan59pn", + "isDeprecated": false, + "rightColumn": 17.0, + "iconName": "filter-list", + "widgetId": "6cy6b27i6c", + "isVisible": true, + "version": 1.0, + "parentId": "0", + "renderMode": "CANVAS", + "isLoading": false, + "borderRadius": "{{appsmith.theme.borderRadius.appBorderRadius}}", + "buttonVariant": "TERTIARY" + } + ] + }, + "layoutOnLoadActions": [ + [ + { + "id": "Admin_agent_stats", + "name": "agent_stats", + "confirmBeforeExecute": false, + "pluginType": "DB", + "jsonPathKeys": [], + "timeoutInMillisecond": 10000.0 + }, + { + "id": "Admin_select_work_ordersPage", + "name": "select_work_ordersPage", + "confirmBeforeExecute": false, + "pluginType": "DB", + "jsonPathKeys": [], + "timeoutInMillisecond": 10000.0 + } + ], + [ + { + "id": "Admin_JSObject1.completedCalc", + "name": "JSObject1.completedCalc", + "collectionId": "Admin_JSObject1", + "confirmBeforeExecute": false, + "pluginType": "JS", + "jsonPathKeys": [ + "async () => {\n await select_work_ordersPage.run();\n await select_work_ordersAgentPage.run();\n let count = 0;\n if (selectAgent.selectedOptionValue.length == 0) count = select_work_ordersPage.data.filter(item => item.completed == \"Yes\").length; else count = select_work_ordersAgentPage.data.filter(item => item.completed == \"Yes\").length;\n storeValue('completedCount', count);\n}" + ], + "timeoutInMillisecond": 10000.0 + }, + { + "id": "Admin_JSObject1.equipChart", + "name": "JSObject1.equipChart", + "collectionId": "Admin_JSObject1", + "confirmBeforeExecute": false, + "pluginType": "JS", + "jsonPathKeys": [ + "async () => {\n await agent_stats.run();\n await agent_statsAgent.run();\n let chartData;\n if (selectAgent.selectedOptionValue.length == 0) chartData = agent_stats.data.map(gen => {\n return {\n x: gen.equipment,\n y: gen.count\n };\n }); else chartData = agent_statsAgent.data.map(gen => {\n return {\n x: gen.equipment,\n y: gen.count\n };\n });\n storeValue('equipmentStats', chartData);\n console.log(appsmith.store.equipmentStats);\n}" + ], + "timeoutInMillisecond": 10000.0 + }, + { + "id": "Admin_JSObject1.totalHoursCalc", + "name": "JSObject1.totalHoursCalc", + "collectionId": "Admin_JSObject1", + "confirmBeforeExecute": false, + "pluginType": "JS", + "jsonPathKeys": [ + "async () => {\n let sum = 0;\n if (selectAgent.selectedOptionValue.length == 0) sum = select_work_ordersPage.data.reduce((accumulator, object) => {\n return accumulator + object.hours;\n }, 0); else sum = select_work_ordersAgentPage.data.reduce((accumulator, object) => {\n return accumulator + object.hours;\n }, 0);\n storeValue('hoursSum', sum);\n}" + ], + "timeoutInMillisecond": 10000.0 + }, + { + "id": "Admin_select_work_ordersAgent", + "name": "select_work_ordersAgent", + "confirmBeforeExecute": false, + "pluginType": "DB", + "jsonPathKeys": [ + " workOrdersTable.pageSize ", + " (workOrdersTable.pageNo - 1) * workOrdersTable.pageSize ", + "selectAgent.selectedOptionValue" + ], + "timeoutInMillisecond": 10000.0 + } + ], + [ + { + "id": "Admin_agent_statsAgent", + "name": "agent_statsAgent", + "confirmBeforeExecute": false, + "pluginType": "DB", + "jsonPathKeys": ["selectAgent.selectedOptionValue"], + "timeoutInMillisecond": 10000.0 + }, + { + "id": "Admin_completed_orders", + "name": "completed_orders", + "confirmBeforeExecute": false, + "pluginType": "DB", + "jsonPathKeys": ["selectAgent.selectedOptionValue"], + "timeoutInMillisecond": 10000.0 + }, + { + "id": "Admin_select_agent", + "name": "select_agent", + "confirmBeforeExecute": false, + "pluginType": "DB", + "jsonPathKeys": [], + "timeoutInMillisecond": 10000.0 + }, + { + "id": "Admin_select_work_orders", + "name": "select_work_orders", + "confirmBeforeExecute": false, + "pluginType": "DB", + "jsonPathKeys": [ + "(workOrdersTable.pageNo - 1) * workOrdersTable.pageSize ", + " workOrdersTable.pageSize " + ], + "timeoutInMillisecond": 10000.0 + }, + { + "id": "Admin_select_work_ordersAgentPage", + "name": "select_work_ordersAgentPage", + "confirmBeforeExecute": false, + "pluginType": "DB", + "jsonPathKeys": ["selectAgent.selectedOptionValue"], + "timeoutInMillisecond": 10000.0 + } + ] + ], + "layoutOnLoadActionErrors": [], + "validOnPageLoadActions": true, + "id": "Admin", + "deleted": false, + "policies": [], + "userPermissions": [] + } + ], + "userPermissions": [], + "policies": [], + "isHidden": true + }, + "deleted": false, + "gitSyncId": "65ee9ce9a207a963066542c7_65ee9d03a207a963066542e4" + } + ], + "actionList": [ + { + "pluginType": "DB", + "pluginId": "postgres-plugin", + "unpublishedAction": { + "name": "total_hours", + "datasource": { + "name": "Mock_DB", + "pluginId": "postgres-plugin", + "messages": [], + "isAutoGenerated": false, + "id": "Mock_DB", + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "pageId": "Admin", + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "SELECT SUM(hours) FROM work_orders where agent={{selectAgent.selectedOptionLabel}};", + "selfReferencingDataPaths": [], + "pluginSpecifiedTemplates": [{ "value": true }] + }, + "executeOnLoad": false, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": ["selectAgent.selectedOptionLabel"], + "userSetOnLoad": false, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "publishedAction": { + "name": "total_hours", + "datasource": { + "name": "Mock_DB", + "pluginId": "postgres-plugin", + "messages": [], + "isAutoGenerated": false, + "id": "Mock_DB", + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "SELECT SUM(hours) FROM work_orders where agent={{selectAgent.selectedOptionLabel}};", + "selfReferencingDataPaths": [], + "pluginSpecifiedTemplates": [{ "value": true }] + }, + "executeOnLoad": false, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": ["selectAgent.selectedOptionLabel"], + "userSetOnLoad": false, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "id": "Admin_total_hours", + "deleted": false, + "gitSyncId": "65ee9ce9a207a963066542c7_65ee9d03a207a963066542f3" + }, + { + "pluginType": "JS", + "pluginId": "js-plugin", + "unpublishedAction": { + "name": "search", + "fullyQualifiedName": "JSObject1.search", + "datasource": { + "name": "UNUSED_DATASOURCE", + "pluginId": "js-plugin", + "organizationId": "61b6d49e33c6ae6163af2716", + "messages": [], + "isAutoGenerated": false, + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "pageId": "Admin", + "collectionId": "Admin_JSObject1", + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "() => {\n if (selectAgent.selectedOptionValue.length == 0) {\n return select_work_orders.data;\n } else {\n return select_work_orders.data.filter(user => user.agent == selectAgent.selectedOptionLabel);\n }\n}", + "selfReferencingDataPaths": [], + "jsArguments": [], + "isAsync": false + }, + "executeOnLoad": false, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": [ + "() => {\n if (selectAgent.selectedOptionValue.length == 0) {\n return select_work_orders.data;\n } else {\n return select_work_orders.data.filter(user => user.agent == selectAgent.selectedOptionLabel);\n }\n}" + ], + "userSetOnLoad": false, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "publishedAction": { + "name": "search", + "fullyQualifiedName": "JSObject1.search", + "datasource": { + "name": "UNUSED_DATASOURCE", + "pluginId": "js-plugin", + "organizationId": "61b6d49e33c6ae6163af2716", + "messages": [], + "isAutoGenerated": false, + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "collectionId": "Admin_JSObject1", + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "() => {\n if (selectAgent.selectedOptionValue.length == 0) {\n return select_work_orders.data;\n } else {\n return select_work_orders.data.filter(user => user.agent == selectAgent.selectedOptionLabel);\n }\n}", + "selfReferencingDataPaths": [], + "jsArguments": [], + "isAsync": false + }, + "executeOnLoad": false, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": [ + "() => {\n if (selectAgent.selectedOptionValue.length == 0) {\n return select_work_orders.data;\n } else {\n return select_work_orders.data.filter(user => user.agent == selectAgent.selectedOptionLabel);\n }\n}" + ], + "userSetOnLoad": false, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "id": "Admin_JSObject1.search", + "deleted": false, + "gitSyncId": "65ee9ce9a207a963066542c7_65ee9d03a207a963066542ed" + }, + { + "pluginType": "DB", + "pluginId": "postgres-plugin", + "unpublishedAction": { + "name": "select_agent", + "datasource": { + "name": "Mock_DB", + "pluginId": "postgres-plugin", + "messages": [], + "isAutoGenerated": false, + "id": "Mock_DB", + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "pageId": "Admin", + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "select * from agent", + "selfReferencingDataPaths": [], + "pluginSpecifiedTemplates": [{ "value": true }] + }, + "executeOnLoad": true, + "dynamicBindingPathList": [], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": [], + "userSetOnLoad": false, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "publishedAction": { + "name": "select_agent", + "datasource": { + "name": "Mock_DB", + "pluginId": "postgres-plugin", + "messages": [], + "isAutoGenerated": false, + "id": "Mock_DB", + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "select * from agent", + "selfReferencingDataPaths": [], + "pluginSpecifiedTemplates": [{ "value": true }] + }, + "executeOnLoad": true, + "dynamicBindingPathList": [], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": [], + "userSetOnLoad": false, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "id": "Admin_select_agent", + "deleted": false, + "gitSyncId": "65ee9ce9a207a963066542c7_65ee9d03a207a963066542f5" + }, + { + "pluginType": "JS", + "pluginId": "js-plugin", + "unpublishedAction": { + "name": "totalHoursCalc", + "fullyQualifiedName": "JSObject1.totalHoursCalc", + "datasource": { + "name": "UNUSED_DATASOURCE", + "pluginId": "js-plugin", + "messages": [], + "isAutoGenerated": false, + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "pageId": "Admin", + "collectionId": "Admin_JSObject1", + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "async () => {\n let sum = 0;\n if (selectAgent.selectedOptionValue.length == 0) sum = select_work_ordersPage.data.reduce((accumulator, object) => {\n return accumulator + object.hours;\n }, 0); else sum = select_work_ordersAgentPage.data.reduce((accumulator, object) => {\n return accumulator + object.hours;\n }, 0);\n storeValue('hoursSum', sum);\n}", + "selfReferencingDataPaths": [], + "jsArguments": [], + "isAsync": true + }, + "executeOnLoad": true, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": [ + "async () => {\n let sum = 0;\n if (selectAgent.selectedOptionValue.length == 0) sum = select_work_ordersPage.data.reduce((accumulator, object) => {\n return accumulator + object.hours;\n }, 0); else sum = select_work_ordersAgentPage.data.reduce((accumulator, object) => {\n return accumulator + object.hours;\n }, 0);\n storeValue('hoursSum', sum);\n}" + ], + "userSetOnLoad": true, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "publishedAction": { + "name": "totalHoursCalc", + "fullyQualifiedName": "JSObject1.totalHoursCalc", + "datasource": { + "name": "UNUSED_DATASOURCE", + "pluginId": "js-plugin", + "messages": [], + "isAutoGenerated": false, + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "collectionId": "Admin_JSObject1", + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "async () => {\n let sum = 0;\n if (selectAgent.selectedOptionValue.length == 0) sum = select_work_ordersPage.data.reduce((accumulator, object) => {\n return accumulator + object.hours;\n }, 0); else sum = select_work_ordersAgentPage.data.reduce((accumulator, object) => {\n return accumulator + object.hours;\n }, 0);\n storeValue('hoursSum', sum);\n}", + "selfReferencingDataPaths": [], + "jsArguments": [], + "isAsync": true + }, + "executeOnLoad": true, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": [ + "async () => {\n let sum = 0;\n if (selectAgent.selectedOptionValue.length == 0) sum = select_work_ordersPage.data.reduce((accumulator, object) => {\n return accumulator + object.hours;\n }, 0); else sum = select_work_ordersAgentPage.data.reduce((accumulator, object) => {\n return accumulator + object.hours;\n }, 0);\n storeValue('hoursSum', sum);\n}" + ], + "userSetOnLoad": true, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "id": "Admin_JSObject1.totalHoursCalc", + "deleted": false, + "gitSyncId": "65ee9ce9a207a963066542c7_65ee9d03a207a96306654311" + }, + { + "pluginType": "DB", + "pluginId": "postgres-plugin", + "unpublishedAction": { + "name": "agent_stats", + "datasource": { + "name": "Mock_DB", + "pluginId": "postgres-plugin", + "messages": [], + "isAutoGenerated": false, + "id": "Mock_DB", + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "pageId": "Admin", + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "SELECT equipment, COUNT(*) FROM work_orders GROUP BY equipment;", + "selfReferencingDataPaths": [], + "pluginSpecifiedTemplates": [{ "value": true }] + }, + "executeOnLoad": true, + "dynamicBindingPathList": [], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": [], + "userSetOnLoad": true, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "publishedAction": { + "name": "agent_stats", + "datasource": { + "name": "Mock_DB", + "pluginId": "postgres-plugin", + "messages": [], + "isAutoGenerated": false, + "id": "Mock_DB", + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "SELECT equipment, COUNT(*) FROM work_orders GROUP BY equipment;", + "selfReferencingDataPaths": [], + "pluginSpecifiedTemplates": [{ "value": true }] + }, + "executeOnLoad": true, + "dynamicBindingPathList": [], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": [], + "userSetOnLoad": true, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "id": "Admin_agent_stats", + "deleted": false, + "gitSyncId": "65ee9ce9a207a963066542c7_65ee9d03a207a963066542f7" + }, + { + "pluginType": "DB", + "pluginId": "postgres-plugin", + "unpublishedAction": { + "name": "update_work_orders1", + "datasource": { + "name": "Mock_DB", + "pluginId": "postgres-plugin", + "messages": [], + "isAutoGenerated": false, + "id": "Mock_DB", + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "pageId": "Admin", + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "UPDATE work_orders\nSET request_date= {{editRequestedDate.formattedDate}}, \n\t\tagent={{editOrderAgent.selectedOptionValue}},\n\t\tmaintenance_notes= {{editNotes.text}},\n\t\tcompleted= {{editCompleted.selectedOptionValue}},\n\t\ttotal_cost= {{editTC.value}},\n\t\tmat_cost= {{editMC.value}},\n\t\thours= {{editHoursUsed.text}}\nWHERE work_id={{workOrdersTable.triggeredRow.work_id}};", + "selfReferencingDataPaths": [], + "pluginSpecifiedTemplates": [{ "value": true }] + }, + "executeOnLoad": false, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": [ + "editHoursUsed.text", + "editTC.value", + "editRequestedDate.formattedDate", + "editMC.value", + "editCompleted.selectedOptionValue", + "editNotes.text", + "workOrdersTable.triggeredRow.work_id", + "editOrderAgent.selectedOptionValue" + ], + "userSetOnLoad": false, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "publishedAction": { + "name": "update_work_orders1", + "datasource": { + "name": "Mock_DB", + "pluginId": "postgres-plugin", + "messages": [], + "isAutoGenerated": false, + "id": "Mock_DB", + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "UPDATE work_orders\nSET request_date= {{editRequestedDate.formattedDate}}, \n\t\tagent={{editOrderAgent.selectedOptionValue}},\n\t\tmaintenance_notes= {{editNotes.text}},\n\t\tcompleted= {{editCompleted.selectedOptionValue}},\n\t\ttotal_cost= {{editTC.value}},\n\t\tmat_cost= {{editMC.value}},\n\t\thours= {{editHoursUsed.text}}\nWHERE work_id={{workOrdersTable.triggeredRow.work_id}};", + "selfReferencingDataPaths": [], + "pluginSpecifiedTemplates": [{ "value": true }] + }, + "executeOnLoad": false, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": [ + "editHoursUsed.text", + "editTC.value", + "editRequestedDate.formattedDate", + "editMC.value", + "editCompleted.selectedOptionValue", + "editNotes.text", + "workOrdersTable.triggeredRow.work_id", + "editOrderAgent.selectedOptionValue" + ], + "userSetOnLoad": false, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "id": "Admin_update_work_orders1", + "deleted": false, + "gitSyncId": "65ee9ce9a207a963066542c7_65ee9d03a207a963066542fb" + }, + { + "pluginType": "JS", + "pluginId": "js-plugin", + "unpublishedAction": { + "name": "completedCalc", + "fullyQualifiedName": "JSObject1.completedCalc", + "datasource": { + "name": "UNUSED_DATASOURCE", + "pluginId": "js-plugin", + "messages": [], + "isAutoGenerated": false, + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "pageId": "Admin", + "collectionId": "Admin_JSObject1", + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "async () => {\n await select_work_ordersPage.run();\n await select_work_ordersAgentPage.run();\n let count = 0;\n if (selectAgent.selectedOptionValue.length == 0) count = select_work_ordersPage.data.filter(item => item.completed == \"Yes\").length; else count = select_work_ordersAgentPage.data.filter(item => item.completed == \"Yes\").length;\n storeValue('completedCount', count);\n}", + "selfReferencingDataPaths": [], + "jsArguments": [], + "isAsync": true + }, + "executeOnLoad": true, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": [ + "async () => {\n await select_work_ordersPage.run();\n await select_work_ordersAgentPage.run();\n let count = 0;\n if (selectAgent.selectedOptionValue.length == 0) count = select_work_ordersPage.data.filter(item => item.completed == \"Yes\").length; else count = select_work_ordersAgentPage.data.filter(item => item.completed == \"Yes\").length;\n storeValue('completedCount', count);\n}" + ], + "userSetOnLoad": true, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "publishedAction": { + "name": "completedCalc", + "fullyQualifiedName": "JSObject1.completedCalc", + "datasource": { + "name": "UNUSED_DATASOURCE", + "pluginId": "js-plugin", + "messages": [], + "isAutoGenerated": false, + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "collectionId": "Admin_JSObject1", + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "async () => {\n await select_work_ordersPage.run();\n await select_work_ordersAgentPage.run();\n let count = 0;\n if (selectAgent.selectedOptionValue.length == 0) count = select_work_ordersPage.data.filter(item => item.completed == \"Yes\").length; else count = select_work_ordersAgentPage.data.filter(item => item.completed == \"Yes\").length;\n storeValue('completedCount', count);\n}", + "selfReferencingDataPaths": [], + "jsArguments": [], + "isAsync": true + }, + "executeOnLoad": true, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": [ + "async () => {\n await select_work_ordersPage.run();\n await select_work_ordersAgentPage.run();\n let count = 0;\n if (selectAgent.selectedOptionValue.length == 0) count = select_work_ordersPage.data.filter(item => item.completed == \"Yes\").length; else count = select_work_ordersAgentPage.data.filter(item => item.completed == \"Yes\").length;\n storeValue('completedCount', count);\n}" + ], + "userSetOnLoad": true, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "id": "Admin_JSObject1.completedCalc", + "deleted": false, + "gitSyncId": "65ee9ce9a207a963066542c7_65ee9d03a207a96306654319" + }, + { + "pluginType": "JS", + "pluginId": "js-plugin", + "unpublishedAction": { + "name": "clear", + "fullyQualifiedName": "JSObject1.clear", + "datasource": { + "name": "UNUSED_DATASOURCE", + "pluginId": "js-plugin", + "messages": [], + "isAutoGenerated": false, + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "pageId": "Admin", + "collectionId": "Admin_JSObject1", + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "() => {\n storeValue('hoursSum', null);\n storeValue('completedCount', null);\n storeValue('equipmentStats', null);\n}", + "selfReferencingDataPaths": [], + "jsArguments": [], + "isAsync": true + }, + "executeOnLoad": false, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": [ + "() => {\n storeValue('hoursSum', null);\n storeValue('completedCount', null);\n storeValue('equipmentStats', null);\n}" + ], + "userSetOnLoad": false, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "publishedAction": { + "name": "clear", + "fullyQualifiedName": "JSObject1.clear", + "datasource": { + "name": "UNUSED_DATASOURCE", + "pluginId": "js-plugin", + "messages": [], + "isAutoGenerated": false, + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "collectionId": "Admin_JSObject1", + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "() => {\n storeValue('hoursSum', null);\n storeValue('completedCount', null);\n storeValue('equipmentStats', null);\n}", + "selfReferencingDataPaths": [], + "jsArguments": [], + "isAsync": true + }, + "executeOnLoad": false, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": [ + "() => {\n storeValue('hoursSum', null);\n storeValue('completedCount', null);\n storeValue('equipmentStats', null);\n}" + ], + "userSetOnLoad": false, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "id": "Admin_JSObject1.clear", + "deleted": false, + "gitSyncId": "65ee9ce9a207a963066542c7_65ee9d03a207a9630665431f" + }, + { + "pluginType": "JS", + "pluginId": "js-plugin", + "unpublishedAction": { + "name": "equipChart", + "fullyQualifiedName": "JSObject1.equipChart", + "datasource": { + "name": "UNUSED_DATASOURCE", + "pluginId": "js-plugin", + "messages": [], + "isAutoGenerated": false, + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "pageId": "Admin", + "collectionId": "Admin_JSObject1", + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "async () => {\n await agent_stats.run();\n await agent_statsAgent.run();\n let chartData;\n if (selectAgent.selectedOptionValue.length == 0) chartData = agent_stats.data.map(gen => {\n return {\n x: gen.equipment,\n y: gen.count\n };\n }); else chartData = agent_statsAgent.data.map(gen => {\n return {\n x: gen.equipment,\n y: gen.count\n };\n });\n storeValue('equipmentStats', chartData);\n console.log(appsmith.store.equipmentStats);\n}", + "selfReferencingDataPaths": [], + "jsArguments": [], + "isAsync": true + }, + "executeOnLoad": true, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": [ + "async () => {\n await agent_stats.run();\n await agent_statsAgent.run();\n let chartData;\n if (selectAgent.selectedOptionValue.length == 0) chartData = agent_stats.data.map(gen => {\n return {\n x: gen.equipment,\n y: gen.count\n };\n }); else chartData = agent_statsAgent.data.map(gen => {\n return {\n x: gen.equipment,\n y: gen.count\n };\n });\n storeValue('equipmentStats', chartData);\n console.log(appsmith.store.equipmentStats);\n}" + ], + "userSetOnLoad": true, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "publishedAction": { + "name": "equipChart", + "fullyQualifiedName": "JSObject1.equipChart", + "datasource": { + "name": "UNUSED_DATASOURCE", + "pluginId": "js-plugin", + "messages": [], + "isAutoGenerated": false, + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "collectionId": "Admin_JSObject1", + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "async () => {\n await agent_stats.run();\n await agent_statsAgent.run();\n let chartData;\n if (selectAgent.selectedOptionValue.length == 0) chartData = agent_stats.data.map(gen => {\n return {\n x: gen.equipment,\n y: gen.count\n };\n }); else chartData = agent_statsAgent.data.map(gen => {\n return {\n x: gen.equipment,\n y: gen.count\n };\n });\n storeValue('equipmentStats', chartData);\n console.log(appsmith.store.equipmentStats);\n}", + "selfReferencingDataPaths": [], + "jsArguments": [], + "isAsync": true + }, + "executeOnLoad": true, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": [ + "async () => {\n await agent_stats.run();\n await agent_statsAgent.run();\n let chartData;\n if (selectAgent.selectedOptionValue.length == 0) chartData = agent_stats.data.map(gen => {\n return {\n x: gen.equipment,\n y: gen.count\n };\n }); else chartData = agent_statsAgent.data.map(gen => {\n return {\n x: gen.equipment,\n y: gen.count\n };\n });\n storeValue('equipmentStats', chartData);\n console.log(appsmith.store.equipmentStats);\n}" + ], + "userSetOnLoad": true, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "id": "Admin_JSObject1.equipChart", + "deleted": false, + "gitSyncId": "65ee9ce9a207a963066542c7_65ee9d03a207a9630665431d" + }, + { + "pluginType": "DB", + "pluginId": "postgres-plugin", + "unpublishedAction": { + "name": "completed_orders", + "datasource": { + "name": "Mock_DB", + "pluginId": "postgres-plugin", + "messages": [], + "isAutoGenerated": false, + "id": "Mock_DB", + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "pageId": "Admin", + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "SELECT COUNT(*) FROM work_orders WHERE agent= {{selectAgent.selectedOptionValue}} and completed ='Yes';", + "selfReferencingDataPaths": [], + "pluginSpecifiedTemplates": [{ "value": true }] + }, + "executeOnLoad": true, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": ["selectAgent.selectedOptionValue"], + "userSetOnLoad": true, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "publishedAction": { + "name": "completed_orders", + "datasource": { + "name": "Mock_DB", + "pluginId": "postgres-plugin", + "messages": [], + "isAutoGenerated": false, + "id": "Mock_DB", + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "SELECT COUNT(*) FROM work_orders WHERE agent= {{selectAgent.selectedOptionValue}} and completed ='Yes';", + "selfReferencingDataPaths": [], + "pluginSpecifiedTemplates": [{ "value": true }] + }, + "executeOnLoad": true, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": ["selectAgent.selectedOptionValue"], + "userSetOnLoad": true, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "id": "Admin_completed_orders", + "deleted": false, + "gitSyncId": "65ee9ce9a207a963066542c7_65ee9d03a207a9630665430f" + }, + { + "pluginType": "DB", + "pluginId": "postgres-plugin", + "unpublishedAction": { + "name": "select_work_ordersAgent", + "datasource": { + "name": "Mock_DB", + "pluginId": "postgres-plugin", + "messages": [], + "isAutoGenerated": false, + "id": "Mock_DB", + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "pageId": "Admin", + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "select * from work_orders where agent = {{selectAgent.selectedOptionValue}} limit {{ workOrdersTable.pageSize }} offset {{ (workOrdersTable.pageNo - 1) * workOrdersTable.pageSize }};", + "selfReferencingDataPaths": [], + "pluginSpecifiedTemplates": [{ "value": true }] + }, + "executeOnLoad": true, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": [ + " workOrdersTable.pageSize ", + " (workOrdersTable.pageNo - 1) * workOrdersTable.pageSize ", + "selectAgent.selectedOptionValue" + ], + "userSetOnLoad": true, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "publishedAction": { + "name": "select_work_ordersAgent", + "datasource": { + "name": "Mock_DB", + "pluginId": "postgres-plugin", + "messages": [], + "isAutoGenerated": false, + "id": "Mock_DB", + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "select * from work_orders where agent = {{selectAgent.selectedOptionValue}} limit {{ workOrdersTable.pageSize }} offset {{ (workOrdersTable.pageNo - 1) * workOrdersTable.pageSize }};", + "selfReferencingDataPaths": [], + "pluginSpecifiedTemplates": [{ "value": true }] + }, + "executeOnLoad": true, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": [ + " workOrdersTable.pageSize ", + " (workOrdersTable.pageNo - 1) * workOrdersTable.pageSize ", + "selectAgent.selectedOptionValue" + ], + "userSetOnLoad": true, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "id": "Admin_select_work_ordersAgent", + "deleted": false, + "gitSyncId": "65ee9ce9a207a963066542c7_65ee9d03a207a96306654313" + }, + { + "pluginType": "DB", + "pluginId": "postgres-plugin", + "unpublishedAction": { + "name": "select_work_orders", + "datasource": { + "name": "Mock_DB", + "pluginId": "postgres-plugin", + "messages": [], + "isAutoGenerated": false, + "id": "Mock_DB", + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "pageId": "Admin", + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "select * from work_orders limit {{ workOrdersTable.pageSize }} offset {{(workOrdersTable.pageNo - 1) * workOrdersTable.pageSize }};", + "selfReferencingDataPaths": [], + "pluginSpecifiedTemplates": [{ "value": true }] + }, + "executeOnLoad": true, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": [ + "(workOrdersTable.pageNo - 1) * workOrdersTable.pageSize ", + " workOrdersTable.pageSize " + ], + "userSetOnLoad": false, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "publishedAction": { + "name": "select_work_orders", + "datasource": { + "name": "Mock_DB", + "pluginId": "postgres-plugin", + "messages": [], + "isAutoGenerated": false, + "id": "Mock_DB", + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "select * from work_orders limit {{ workOrdersTable.pageSize }} offset {{(workOrdersTable.pageNo - 1) * workOrdersTable.pageSize }};", + "selfReferencingDataPaths": [], + "pluginSpecifiedTemplates": [{ "value": true }] + }, + "executeOnLoad": true, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": [ + "(workOrdersTable.pageNo - 1) * workOrdersTable.pageSize ", + " workOrdersTable.pageSize " + ], + "userSetOnLoad": false, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "id": "Admin_select_work_orders", + "deleted": false, + "gitSyncId": "65ee9ce9a207a963066542c7_65ee9d03a207a96306654305" + }, + { + "pluginType": "DB", + "pluginId": "postgres-plugin", + "unpublishedAction": { + "name": "select_work_ordersPage", + "datasource": { + "name": "Mock_DB", + "pluginId": "postgres-plugin", + "messages": [], + "isAutoGenerated": false, + "id": "Mock_DB", + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "pageId": "Admin", + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "select * from work_orders;", + "selfReferencingDataPaths": [], + "pluginSpecifiedTemplates": [{ "value": true }] + }, + "executeOnLoad": true, + "dynamicBindingPathList": [], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": [], + "userSetOnLoad": true, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "publishedAction": { + "name": "select_work_ordersPage", + "datasource": { + "name": "Mock_DB", + "pluginId": "postgres-plugin", + "messages": [], + "isAutoGenerated": false, + "id": "Mock_DB", + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "select * from work_orders;", + "selfReferencingDataPaths": [], + "pluginSpecifiedTemplates": [{ "value": true }] + }, + "executeOnLoad": true, + "dynamicBindingPathList": [], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": [], + "userSetOnLoad": true, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "id": "Admin_select_work_ordersPage", + "deleted": false, + "gitSyncId": "65ee9ce9a207a963066542c7_65ee9d03a207a96306654315" + }, + { + "pluginType": "DB", + "pluginId": "postgres-plugin", + "unpublishedAction": { + "name": "agent_statsAgent", + "datasource": { + "name": "Mock_DB", + "pluginId": "postgres-plugin", + "messages": [], + "isAutoGenerated": false, + "id": "Mock_DB", + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "pageId": "Admin", + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "SELECT equipment, COUNT(*) FROM work_orders WHERE agent= {{selectAgent.selectedOptionValue}} GROUP BY equipment;", + "selfReferencingDataPaths": [], + "pluginSpecifiedTemplates": [{ "value": true }] + }, + "executeOnLoad": true, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": ["selectAgent.selectedOptionValue"], + "userSetOnLoad": true, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "publishedAction": { + "name": "agent_statsAgent", + "datasource": { + "name": "Mock_DB", + "pluginId": "postgres-plugin", + "messages": [], + "isAutoGenerated": false, + "id": "Mock_DB", + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "SELECT equipment, COUNT(*) FROM work_orders WHERE agent= {{selectAgent.selectedOptionValue}} GROUP BY equipment;", + "selfReferencingDataPaths": [], + "pluginSpecifiedTemplates": [{ "value": true }] + }, + "executeOnLoad": true, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": ["selectAgent.selectedOptionValue"], + "userSetOnLoad": true, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "id": "Admin_agent_statsAgent", + "deleted": false, + "gitSyncId": "65ee9ce9a207a963066542c7_65ee9d03a207a9630665431b" + }, + { + "pluginType": "DB", + "pluginId": "postgres-plugin", + "unpublishedAction": { + "name": "select_work_ordersAgentPage", + "datasource": { + "name": "Mock_DB", + "pluginId": "postgres-plugin", + "messages": [], + "isAutoGenerated": false, + "id": "Mock_DB", + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "pageId": "Admin", + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "select * from work_orders where agent = {{selectAgent.selectedOptionValue}};", + "selfReferencingDataPaths": [], + "pluginSpecifiedTemplates": [{ "value": true }] + }, + "executeOnLoad": true, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": ["selectAgent.selectedOptionValue"], + "userSetOnLoad": true, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "publishedAction": { + "name": "select_work_ordersAgentPage", + "datasource": { + "name": "Mock_DB", + "pluginId": "postgres-plugin", + "messages": [], + "isAutoGenerated": false, + "id": "Mock_DB", + "deleted": false, + "policies": [], + "userPermissions": [] + }, + "actionConfiguration": { + "timeoutInMillisecond": 10000.0, + "paginationType": "NONE", + "encodeParamsToggle": true, + "body": "select * from work_orders where agent = {{selectAgent.selectedOptionValue}};", + "selfReferencingDataPaths": [], + "pluginSpecifiedTemplates": [{ "value": true }] + }, + "executeOnLoad": true, + "dynamicBindingPathList": [{ "key": "body" }], + "isValid": true, + "invalids": [], + "messages": [], + "jsonPathKeys": ["selectAgent.selectedOptionValue"], + "userSetOnLoad": true, + "confirmBeforeExecute": false, + "policies": [], + "userPermissions": [], + "createdAt": "2024-03-11T05:56:19Z" + }, + "id": "Admin_select_work_ordersAgentPage", + "deleted": false, + "gitSyncId": "65ee9ce9a207a963066542c7_65ee9d03a207a96306654317" + } + ], + "actionCollectionList": [ + { + "unpublishedCollection": { + "name": "JSObject1", + "pageId": "Admin", + "pluginId": "js-plugin", + "pluginType": "JS", + "actions": [], + "archivedActions": [], + "body": "export default {\n\tmyVar1: [],\n\tmyVar2: {},\n\t\n\tclear: () => {\n\t\tstoreValue('hoursSum',null);\n\t\tstoreValue('completedCount',null);\n\t\tstoreValue('equipmentStats',null);\n\t},\n\t\n\tsearch: () => {\n\t\tif(selectAgent.selectedOptionValue.length==0){\n\t\t\treturn select_work_orders.data\n\t\t}\n\t\telse{\n\t\t\treturn(select_work_orders.data.filter(user => user.agent==(selectAgent.selectedOptionLabel)))\n\t\t}\n\t},\n\t\n\ttotalHoursCalc: async() => {\n\t\tlet sum = 0\n\t\tif(selectAgent.selectedOptionValue.length == 0)\n\t sum = select_work_ordersPage.data.reduce((accumulator, object) => {\n return accumulator + object.hours;\n}, 0);\n\t\telse \n\t\t\tsum = select_work_ordersAgentPage.data.reduce((accumulator, object) => {\n return accumulator + object.hours;\n}, 0);\n\t\t\t storeValue('hoursSum',sum);\n\n\t},\n\n\tcompletedCalc: async() => {\t\n\t\tawait select_work_ordersPage.run()\n\t\tawait select_work_ordersAgentPage.run()\n\t\tlet count = 0\n\n\t\tif(selectAgent.selectedOptionValue.length == 0)\n\t count = (select_work_ordersPage.data.filter((item) => item.completed == \"Yes\")).length;\n\t\telse \n\t\tcount = (select_work_ordersAgentPage.data.filter((item) => item.completed == \"Yes\")).length;\n\n storeValue('completedCount',count);\n\t},\n\t\n\tequipChart: async() => {\n\t\tawait agent_stats.run()\n\t\tawait agent_statsAgent.run()\n\t\tlet chartData\n\t\tif(selectAgent.selectedOptionValue.length == 0)\n\t chartData = agent_stats.data.map((gen) => {return {x: gen.equipment, y: gen.count }})\n\n\t\telse \n\t\tchartData = agent_statsAgent.data.map((gen) => {return {x: gen.equipment, y: gen.count }})\n\n storeValue('equipmentStats',chartData);\n\t\tconsole.log(appsmith.store.equipmentStats)\n\t}\n\t\n}", + "variables": [ + { "name": "myVar1", "value": "[]" }, + { "name": "myVar2", "value": "{}" } + ], + "userPermissions": [] + }, + "publishedCollection": { + "name": "JSObject1", + "pluginId": "js-plugin", + "pluginType": "JS", + "actions": [], + "archivedActions": [], + "body": "export default {\n\tmyVar1: [],\n\tmyVar2: {},\n\t\n\tclear: () => {\n\t\tstoreValue('hoursSum',null);\n\t\tstoreValue('completedCount',null);\n\t\tstoreValue('equipmentStats',null);\n\t},\n\t\n\tsearch: () => {\n\t\tif(selectAgent.selectedOptionValue.length==0){\n\t\t\treturn select_work_orders.data\n\t\t}\n\t\telse{\n\t\t\treturn(select_work_orders.data.filter(user => user.agent==(selectAgent.selectedOptionLabel)))\n\t\t}\n\t},\n\t\n\ttotalHoursCalc: async() => {\n\t\tlet sum = 0\n\t\tif(selectAgent.selectedOptionValue.length == 0)\n\t sum = select_work_ordersPage.data.reduce((accumulator, object) => {\n return accumulator + object.hours;\n}, 0);\n\t\telse \n\t\t\tsum = select_work_ordersAgentPage.data.reduce((accumulator, object) => {\n return accumulator + object.hours;\n}, 0);\n\t\t\t storeValue('hoursSum',sum);\n\n\t},\n\n\tcompletedCalc: async() => {\t\n\t\tawait select_work_ordersPage.run()\n\t\tawait select_work_ordersAgentPage.run()\n\t\tlet count = 0\n\n\t\tif(selectAgent.selectedOptionValue.length == 0)\n\t count = (select_work_ordersPage.data.filter((item) => item.completed == \"Yes\")).length;\n\t\telse \n\t\tcount = (select_work_ordersAgentPage.data.filter((item) => item.completed == \"Yes\")).length;\n\n storeValue('completedCount',count);\n\t},\n\t\n\tequipChart: async() => {\n\t\tawait agent_stats.run()\n\t\tawait agent_statsAgent.run()\n\t\tlet chartData\n\t\tif(selectAgent.selectedOptionValue.length == 0)\n\t chartData = agent_stats.data.map((gen) => {return {x: gen.equipment, y: gen.count }})\n\n\t\telse \n\t\tchartData = agent_statsAgent.data.map((gen) => {return {x: gen.equipment, y: gen.count }})\n\n storeValue('equipmentStats',chartData);\n\t\tconsole.log(appsmith.store.equipmentStats)\n\t}\n\t\n}", + "variables": [ + { "name": "myVar1", "value": "[]" }, + { "name": "myVar2", "value": "{}" } + ], + "userPermissions": [] + }, + "id": "Admin_JSObject1", + "deleted": false, + "gitSyncId": "65ee9ce9a207a963066542c7_65ee9d03a207a96306654325" + } + ], + "editModeTheme": { + "name": "Default-New", + "displayName": "Modern", + "isSystemTheme": true, + "deleted": false + }, + "publishedTheme": { + "name": "Default-New", + "displayName": "Modern", + "isSystemTheme": true, + "deleted": false + } +}