188 lines
5.7 KiB
Smalltalk
188 lines
5.7 KiB
Smalltalk
Class {
|
|
#name : #GtCarpCoderModel,
|
|
#superclass : #GtSourceCoder,
|
|
#instVars : [
|
|
'pharoBindings',
|
|
'carpLinkApplicationStrategy',
|
|
'exception',
|
|
'application',
|
|
'commandFactory'
|
|
],
|
|
#category : #'Carp-Coder'
|
|
}
|
|
|
|
{ #category : #'instance creation' }
|
|
GtCarpCoderModel class >> code: aString [
|
|
|
|
^ self new sourceCode:
|
|
(GtCoderExplicitStringSource new source: aString)
|
|
]
|
|
|
|
{ #category : #converting }
|
|
GtCarpCoderModel >> asCoderViewModel [
|
|
|
|
^ GtSourceCoderViewModel new coder: self
|
|
]
|
|
|
|
{ #category : #accessing }
|
|
GtCarpCoderModel >> bindAndExecute: sourceString [
|
|
"Answer the source code with all declared variables returned in an immediate dictionary"
|
|
|
|
<gtIgnoreConstraint: #GtRBAcceptVisitorCalledFromNonVisitingMethods>
|
|
<remoteDebuggerSignal>
|
|
| res trimmedSource ast varNames lastStatement carpSource |
|
|
trimmedSource := SmaCCString on: sourceString trimRight.
|
|
ast := CarpParser parse: trimmedSource. "The variables to be returned are names that are in pharoBindings"
|
|
varNames := pharoBindings bindingNames asSet. "Assign the final statement to snippetResult"
|
|
lastStatement := ast expressions last.
|
|
trimmedSource
|
|
insert: '(defdynamic snippetResult '
|
|
at: lastStatement startPosition.
|
|
trimmedSource insert: ')' at: lastStatement stopPosition.
|
|
varNames add: 'snippetResult'. "Get the final source to execute"
|
|
carpSource := self
|
|
sourceFrom: trimmedSource asString
|
|
returnedVarNames: varNames.
|
|
res := self bindAndExecuteRaw: sourceString.
|
|
|
|
(res at: #result) = 'success' ifTrue: [ ^ CarpExecutionResult from: res ].
|
|
exception := (PharoLinkRemoteError new
|
|
application: application;
|
|
command: commandFactory command;
|
|
trace: (res at: #value)).
|
|
exception signal
|
|
]
|
|
|
|
{ #category : #accessing }
|
|
GtCarpCoderModel >> bindAndExecuteRaw: sourceString [
|
|
application := carpLinkApplicationStrategy applicationServer.
|
|
application isRunning ifFalse: [ application start ].
|
|
commandFactory := application newCommandFactory.
|
|
|
|
^ commandFactory
|
|
<< sourceString;
|
|
sendAndWait
|
|
]
|
|
|
|
{ #category : #accessing }
|
|
GtCarpCoderModel >> carpLinkApplicationStrategy: anApplicationStrategy [
|
|
carpLinkApplicationStrategy := anApplicationStrategy
|
|
]
|
|
|
|
{ #category : #accessing }
|
|
GtCarpCoderModel >> computeAst: theSourceString [
|
|
^ CarpParser
|
|
parseWithErrors: theSourceString
|
|
]
|
|
|
|
{ #category : #accessing }
|
|
GtCarpCoderModel >> exception [
|
|
^ exception
|
|
]
|
|
|
|
{ #category : #accessing }
|
|
GtCarpCoderModel >> initializeAddOns: addOns [
|
|
super initializeAddOns: addOns.
|
|
|
|
addOns
|
|
addStyler: (GtCoderAstSmaCCParserStyler new smaccStyler: CarpParser gtStyler).
|
|
|
|
addOns
|
|
addMainAction: 'Evaluate' translated
|
|
icon: BrGlamorousVectorIcons play
|
|
action: [ :aCoderUIModel :anElement |
|
|
GtCoderCodeExecutor doIt
|
|
coderViewModel: aCoderUIModel;
|
|
element: anElement;
|
|
execute ]
|
|
id: GtSourceCoderDoItActionId.
|
|
addOns
|
|
addMainAction: 'Inspect' translated
|
|
icon: BrGlamorousVectorIcons playinspect
|
|
action: [ :aCoderUIModel :anElement |
|
|
GtCoderCodeExecutor doItAndGo
|
|
coderViewModel: aCoderUIModel;
|
|
element: anElement;
|
|
execute ]
|
|
id: GtSourceCoderDoItAndGoActionId.
|
|
addOns
|
|
addMainAction: 'Expand Macros' translated
|
|
icon: BrGlamorousVectorIcons repair
|
|
action: [ :aCoderUIModel :anElement |
|
|
| source |
|
|
source := '(expand ''' , sourceCode currentSourceText value text , ')'.
|
|
anElement phlow
|
|
spawnObject: ((self bindAndExecute: source) parse view: #gtSourceFor:) ]
|
|
id: #'source-coder--macro-expand-action'.
|
|
addOns
|
|
addMainAction: 'Build and Run' translated
|
|
icon: BrGlamorousVectorIcons refresh
|
|
action: [ :aCoderUIModel :anElement |
|
|
| source |
|
|
source := '' , sourceCode currentSourceText value text , '(build) (run)'.
|
|
anElement phlow
|
|
spawnObject: (CarpCliOutput text: ((self bindAndExecuteRaw: source) at: 'value')) ]
|
|
id: #'source-coder--build-and-run-action'.
|
|
addOns
|
|
addMainAction: 'Infer Type' translated
|
|
icon: BrGlamorousVectorIcons inspect
|
|
action: [ :aCoderUIModel :anElement | self inspectTypeSpawningOn: anElement phlow]
|
|
id: #'source-coder--type-infer-action'
|
|
]
|
|
|
|
{ #category : #accessing }
|
|
GtCarpCoderModel >> initializeShortcuts: addOns [
|
|
super initializeShortcuts: addOns.
|
|
|
|
addOns
|
|
addShortcut: GtSourceCoderDoItShortcut new;
|
|
addShortcut: GtSourceCoderDoItAndInspectShortcut new
|
|
]
|
|
|
|
{ #category : #accessing }
|
|
GtCarpCoderModel >> inspectTypeSpawningOn: aPhlow [
|
|
| source ast |
|
|
source := sourceCode currentSourceText value text.
|
|
ast := CarpParser parse: source.
|
|
|
|
(ast expressions size = 1 and: [ ast expressions first isDefinition ])
|
|
ifTrue: [ self bindAndExecute: source asString.
|
|
source := ast expressions first definitionVariable value source ].
|
|
|
|
source := '(def *type-infer-this* ' , source
|
|
, ') (defdynamic *type-infer-result* (type *type-infer-this*)) (def *type-infer-this* 0) *type-infer-result*'.
|
|
aPhlow spawnObject: ((self bindAndExecute: source) parse transformValue: [:aValue | CarpTypeSignature on: aValue expressions first using: self])
|
|
]
|
|
|
|
{ #category : #accessing }
|
|
GtCarpCoderModel >> newCompletionStrategy [
|
|
^ GtCompletionStrategy new
|
|
]
|
|
|
|
{ #category : #accessing }
|
|
GtCarpCoderModel >> pharoBindings: anObject [
|
|
pharoBindings := anObject
|
|
]
|
|
|
|
{ #category : #accessing }
|
|
GtCarpCoderModel >> primitiveEvaluate: aSourceString inContext: aGtSourceCoderEvaluationContext onFailDo: anEvaluationFailBlock [
|
|
^ (self bindAndExecute: aSourceString) parse
|
|
transformValue: [ :aValue | aValue expressions first toPharo ]
|
|
]
|
|
|
|
{ #category : #accessing }
|
|
GtCarpCoderModel >> sourceFrom: trimmedSourceString returnedVarNames: varNames [
|
|
"Answer the modified source to return the declared variables"
|
|
|
|
^ String
|
|
streamContents: [ :stream |
|
|
stream << trimmedSourceString.
|
|
stream lf << 'snippetResult' ]
|
|
]
|
|
|
|
{ #category : #accessing }
|
|
GtCarpCoderModel >> variableBindings: aGtSnippetBindings [
|
|
|
|
^ self pharoBindings: aGtSnippetBindings
|
|
]
|