go to post Joel Solon · Dec 30, 2016 Files are now also here: https://github.com/joelsolon/DevCommunity/tree/master/AppMon
go to post Joel Solon · Dec 1, 2016 Here is some information about debugging CSP pages using Studio. I actually just taught this to students in class yesterday!1. You can't set a breakpoint inside the ObjectScript on a CSP page (inside a <script> tag). But the workaround for this is to use the View > View Other Code and load the class definition that's generated from the CSP page. Then you can set breakpoints normally.2. Once you've set breakpoints, you can set your CSP page as the Debugging Target, and launch it directly from Studio. The page runs in a special "debug mode". This means that the normal timeouts (typically 60 seconds) are suspended, so that the browser and the CSP Gateway will wait as long as necessary while you step through the code.You can step through the code that is called when the page is first being built, and you can also step through code that is called via a hyperevent.The only issue with stepping through the code is that Studio does not seem to be highlighting the current line as it normally does. I think this used to work fine, so I may bring this up with the developers. But a workaround for now is to use the "Call Stack" tab of the Watch Window. The top line of the call stack shows the label+offset of the current line. As you step, the top line is updated with the current label+offset. You can simply click the top line whenever you want and the Code Window will scroll to that line, also showing you the current values of the variables.
go to post Joel Solon · Oct 14, 2016 Option #1 is "store all persons together in the same global." So, people that are just regular persons, as well as presidents, senators, and representatives, are all stored together, with a single shared ID sequence. Optionally adding [Abstract] to the Person class prevents persons from being created/stored; there will be only presidents, senators, and representatives. With or without [Abstract], adding the bitmap extent index allows quick retrieval of different types of persons.Option #2 is "store different types of persons in separate globals." Kyle's original description of how to do this is correct. Similar to using [Abstract] for option #1, optionally adding [NoExtent] for this option prevents persons from being stored. So the global structure you show in your first question is correct. Omitting [NoExtent] doesn't change that. You don't have to also use [Abstract] for option #2, but you can.
go to post Joel Solon · Sep 9, 2016 I thought IKnow required a special license. Can I really do all of this with my regular old Caché license?
go to post Joel Solon · Sep 6, 2016 In the process of writing this article, I discovered that our documentation on these two keywords contains the following sentence: "When you compile this class alone, the compiler does not cause the other classes to be compiled." That sentence is incorrect. The documentation has now been fixed, and the updated information will be available online when we refresh the online content.
go to post Joel Solon · Sep 6, 2016 Another variation is where the USA.Person class is marked Abstract (so there are no objects/rows that are only Persons). For Kyle's Option #1, we'll make USA.President, USA.Senator, and USA.Representative subclasses of USA.Person. All the politicians will be stored together in the ^USA.PersonD global, with each type marked using the "~USA.President~"-style syntax. Without the bitmap extent index, finding all Senators requires looking through the entire global. With it, there is a bitmap index for each type of politician. Note that this variation provides 4 tables: Person (showing the common data for all politicians), and President, Senator, Representative (showing all the data for each type, including the Person data).For Kyle's Option #2, the subclasses inherit from %Persistent and USA.Person, and each type of politician is stored separately from the other types. When doing this, you would normally specify [NoExtent] for the USA.Person class. There won't be a Person table in this case.
go to post Joel Solon · Sep 1, 2016 Usually the variable subscripts in a global will have a name of some kind, known to the developers that wrote or support the application. The name may also be known to the users of the application. I recommend using that name for the property, such as "EmpID" or "EmployeeID" rather than something generic like "Sub2".
go to post Joel Solon · Aug 4, 2016 If your class inherits properties from another class, substitute %compiledclass for %class in the solution above.
go to post Joel Solon · Aug 4, 2016 The default behavior for %Save() in Caché classes is still to use $Increment, which will be fine for many cases. $Sequence is intended for cases where the volume and speed of inserts is very very high.
go to post Joel Solon · Aug 4, 2016 Very good article that really shows the benefits of $sequence. Do you have an explanation for why the calls to LastName() and FirstName() went from 16.8 sec (using $increment) down to 8.2 sec (using $sequence)?Also, there's a typo: "acquisitoin" should be "acquisition".
go to post Joel Solon · Jun 6, 2016 This is interesting stuff and it's good to revisit this as ObjectScript evolves. In the old days, there was advice about things like this:set a=1, b=1, c=1 was faster than set (a, b, c) =1if a]"" was faster than if a'=""etc.But we always reminded people that these things could change from platform to platform, and that extra database references were usually much costlier than the differences between coding things one way vs another.So, Tim, if you've got the time, please tell the Community if your tests show different values on Windows vs Linux vs Unix vs OS X. And (this might be harder), give us your opinion on a "tipping point" or a "when to care about this point"; that is, if the delimited or list string has fewer than N pieces/items, it really doesn't matter which method is used, but above N, use the $listlength method, and above M, use $listnext. Something like that.
go to post Joel Solon · May 2, 2016 I never updated this post with the workaround, sorry! The problem is with Secure Storage. You can reset it by going into Atelier > Preferences > General > Security > Secure Storage. Click the Contents tab. Under com.intersys.eclipse.connmgr, you'll see an entry for the connection to the Caché server. Delete that entry, and you should be able to recreate the server connection.
go to post Joel Solon · Apr 8, 2016 Spoke too soon. Trying to delete or edit a broken connection fails. I am reporting this.
go to post Joel Solon · Apr 8, 2016 Server Explorer exists on the Mac and was open. I had only used it to explore the contents of the server. But it also allows editing and deleting of the server connection itself. Thanks!
go to post Joel Solon · Feb 22, 2016 Also note that Caché developers will be able to choose to use Atelier even if the Caché server is not yet on v2016.2 or a later version. Steps:Use a local installation of v2016.2 integrated with their chosen source control system to edit classes and routines.Use Atelier’s export feature to export the file(s) to our standard XML format, and import those files on the Caché server.Each developer can choose between familiarity with Studio and easy integration with the server (with perhaps no integration with source control), or familiarity with Eclipse and easy integration with source control (with an extra step or two to integrate with the Caché server).
go to post Joel Solon · Feb 17, 2016 Small comment: use $this instead of ##this, even though they compile to the same thing.