[squeak-dev] More Installer and Sake/Packages documentation

Ken G. Brown kbrown at mac.com
Sat Nov 7 23:06:45 UTC 2009


For those who cannot be bothered to look in an Image for 
documentation, here are some of the
Class Comments retrieved from an 090628-1523_Squeak3.10.2-lpf-atomic 
image from 
<ftp://ftp.squeak.org/3.11/Squeak3.10.2-lpf-atomic/latest/> after 
executing Installer install: 'Packages'.
This is also being posted to <http://squeaktipsandtrickswatch.blogspot.com/>.

Ken G. Brown

--
Installer-Core/Installer

Documentation now available at http://installer.pbwiki.com/Installer

useFileIn - flag to load source.st rather than using Monticello

--
Installer-Core/InstallerMantis

Search feature is based upon a custom mantis query ceveloped and 
maintained by Ken Causey <ken at kencausey.com>

Installer mantis bugsAll select: [ :ea | ea status = 'testing' ].

--
Installer-Formats/SARInstaller

I am an object that handles the loading of SAR (Squeak ARchive) files.

A SAR file is a Zip file that follows certain simple conventions:

* it may have a member named "install/preamble".

This member, if present, will be filed in as Smalltalk source code at 
the beginning of installation.
Typically, the code in the preamble will make whatever installation 
preparations are necessary,
and will then call methods in the "client services" method category 
to extract or install other zip members.

* It may have a member named "install/postscript".

This member, if present, will be filed in as Smalltalk source code at 
the end of installation.
Typically, the code in the postscript will set up the operating environment,
and will perhaps put objects in flaps, open projects or README files, 
or launch samples.

Within the code in the preamble and postscript, "self" is set to the 
instance of the SARInstaller.

If neither an "install/preamble" nor an "install/postscript" file is present,
all the members will be installed after prompting the user,
based on a best guess of the member file types that is based on 
member filename extensions.

This is new behavior.

--
Installer-Scripts/InstallerScripts

(self new addPackage: 'Example') options collect: [ :ea  | ea value 
asLegalSelector asSymbol ]  #(#scriptExampleSqueak310forKPH 
#scriptExampleSqueak310 #scriptExampleSqueak310)

--
Installer-Launcher/Launcher

A Launcher provides squeak with a range of capabilities that are 
intended to be used from the command line.

As a design goal, the startup process can invoke Launcher several 
times at several points in the startup sequence. In particular 1) 
below aims to provide a mechanism for getting in to images that are 
broken in some form, so as to enable a script to be run before 
morphic has attempted to startup.

1) Launcher is registered to handle startup notification after Security manager
any class which wishes to provide a service to be usable at this time 
implements startFrom:

2) Launcher is wired in to ProjectLauncher to handle startup 
notification when squeak is fully initialized. Any class wishing to 
provide a service to be usable at this time implements launchFrom:

#startFrom: and #launchFrom: are called providing a handle to the 
launcher which may be used to obtain parameters using the desired 
scheme.

a) launcher getParameters . key=value +yes -no
b) launcher getParametersOldStyle . key value key2 value2

Instance Variables
	actionSelector: #startFrom: #launchFrom:
	commandLineClass: aClass
	image:	the smalltalk image or self if being a mock
	mock: the mock array of startup parameters
	nextCommandLineDocument: aString
	nextParameterIndex:	 anInteger

--
Sake-Core/SakeBlock

Raise this if for some reason you find that the task you are doing is 
blocked. This might occur in a multi builder build system where two 
building threads decide to build the same item.

(implementation idea - not implemented yet)

When a Block is detected, Sake, looks for any following dependent 
task that is not dependant upon the blocked task.

Alternatively, Sake could simply randomise the task order and re-sort 
them, tryng again.

--
Sake-Core/SakeCompiler

Enables methods to include raw uncompiled text for documentation 
purposes following a line containing 6 quotes """"""

--
Sake-Core/SakeMeta

I'm a dictionary which can be used using any method call instead of 
#at:put: and at:. Use me like:

- (aSakeMeta foo: 'bar') which is equivalent to (aSakeMeta at: 'foo' 
put: 'bar')
- (aSakeMeta foo) which is equivalent to (aSakeMeta at: 'foo')

The instance variable 'order' remembers the order in which the 
elements have been added. The methods #withIndexDo: and #printOn: use 
this variable to iterate in the same order.

| s |
s := ReadWriteStream on: String new.
(self new a: 1; b: 2; yourself) storeOn: s.
s reset contents

--
Sake-Core/SakeTask

SakeTasks are typically defined as class side methods, which return 
an instance of SakeTask.

To obtain a list of available tasks, do "Senders of #define: "

MyClass-task1: aParameter

	^ SakeTask define: [ :task |
			task dependsOn: {self ruleL3.}.
			task if: [ <return true if action is needed> ].
	    	task action: [ <do something> ]
	  ]

The 'unique id' of a task is the method context in which it is 
instanciated, and its paramters.
Therefore only one task should be instanciated per method.

Note: Sake tasks can have parameters, Rake tasks dont.

To execute a task...

(MyClass task1: 'param') run.

Results of the prior tasks are available via #results.

FAQ
====
How can I call one Sake task from inside another task?

Generally, if you want invoke one task from another task, the proper 
way to do that is to include the task to be invoked as a prerequisite 
of the task doing the invoking.

For example:

MyTasks-c-#taskPrimary

^ SakeTask define: [ :task |
	task dependsOn: { self taskSecondary }.
	task action: [ self log sake: 'Doing Primary Task'. ].
]

MyTasks-c-#taskSecondary
^ SakeTask define: [ :task |
	task action: [ self log sake: 'Doing Secondary Task' ].
]

In this case, if the secondary task fails, the whole task stops.

Secondary tasks can also be passed to the ifBlock. In that case, if 
the task succeeds then the action is performed, if the task fails 
then the action is considered not needed.

^ SakeTask define: [ :task |
	task if: { self taskSecondary }.
	task action: [ self log sake: 'Doing Primary Task'. ].
]

Action, can also take a list of tasks.

^ SakeTask define: [ :task |
	task action: {
	                 self taskSecondary.
	                 [ self log sake: 'Doing Primary Task' ].  "a block task"
				}
].



--
Sake-Packages/Packages

Sake/Packages usage:

Definitions Search Path
============================
Packages named: 'PackageName'.

Will obtain a package definition. Subclasses of Packages are searched 
using the order defined by #findPath which is specified by #priority.

e.g. Packages findPath => {PackagesSqueak310 . PackagesDev . 
PackagesAll . PackagesSeaside29}

Packages-#priority is used to sort classes like so:

The class with defns for a relevant version (listed in 
#relevantVersions) => 100
The class with defns for dev version (PackagesDev) => 400
The class with defns for all versions (PackagesAll) => 500

Additional package "universes" can define their own priority in order 
to specify where to appear in the #findPath.
PackagesSeaside29
PackagesGjaller
PackagesBeach

Usage:
========
verbose usage specifying run style.

(Packages named: 'Seaside') run.  " or runQuietly, runStepping, runLogging"

#runStepping , - presents a confirm/debug dialog before each action.
#run            - default.
#runQuietly    - auto-confirms any SakeConfirm dialogs.
#runLogging   - Writes any SakeStop warnings to self log.

default usage:

Packages load: 'Seaside'.
Packages latest: 'Seaside'. "as above, but use latest versions of everything"
Packages unload: 'Seaside'.

multiples:

Packages load: #('Seaside' 'Magma' 'Logging') 

Unloading
========
Unloading comes in two variants.

Each package task loaded by Sake/Packages is remembered in the 'provided' list
If you perform:

     Packages unload: 'Seaside' .

     Packages unloadStepping: 'Seaside' .

Then the 'historical' unload scripts are used, as defined when the 
original load tasks were run.

If instead you perform:

     (Packages current named: 'Seaside') beUnloading runStepping.

Then the most recently defined unload script will be run.

Note: If packages such as "Magma server" and "Magma client" provides 
"Magma", then

     Packages unload: 'Magma'.

Will unload whichever of the two are loaded.
===
Misc notes...

Universes are using 'instance side' task definition, so the task 
extensions mechanism does not work in this context.

If a package appears in Packages under an obscure name, it can
tell the PackageInfo instance what name was used to load it via #mcName:

If a package has a version number with a '+' after it, then 'Packages 
upgrade' will always attempt to load the latest code, leaving 
Monticello to determine if there are any code changed that need to be 
applied.

To generate all of the methods based upon universes definitions:

  	Packages taskGenerateAllUniverses run.
	or
	Packages taskGenerateAll  run.

--
Packages-Library/PackagesDevU

Package definitions for this version as obtained automatically from 
the Universes server.

To override the definitions in the univere add to my subclass in 
PackagesSqueak310

To re-read the package definitions from the universes server.

self taskGeneratePackageTasks run

--

-------------- next part --------------
An HTML attachment was scrubbed...
URL: http://lists.squeakfoundation.org/pipermail/squeak-dev/attachments/20091107/50955a9e/attachment.htm


More information about the Squeak-dev mailing list