The Wiert Corner – irregular stream of stuff

Jeroen W. Pluimers on .NET, C#, Delphi, databases, and personal interests

  • My badges

  • Twitter Updates

  • My Flickr Stream

  • Pages

  • All categories

  • Enter your email address to subscribe to this blog and receive notifications of new posts by email.

    Join 1,839 other subscribers

Archive for the ‘Software Development’ Category

Can we truly assert that an array returned from a function is always a true copy?

Posted by jpluimers on 2020/09/23

The answer is no: [WayBack] Hi all, Can we truly assert that an array returned from a function is always a new true copy and that this is guaranteed to not change in between compil… – Ugochukwu Mmaduekwe – Google+

From Primož book and comment:

Depending on how you create this array.

For example, the following code outputs 42, not 17.

program Project142;

{$APPTYPE CONSOLE}

{$R *.res}

uses
System.SysUtils;

function Bypass(const a: TArray<integer>): TArray<integer>;
begin
Result := a;
end;

var
a, b: TArray<integer>;

begin
SetLength(a, 1);
a[0] := 17;
b := Bypass(a);
a[0] := 42;
Writeln(b[0]);
Readln;
end.

You can use `SetLength(arr, Length(arr))` to make array unique. Changing Bypass to the following code would make the test program emit 17.

function Bypass(const a: TArray<integer>): TArray<integer>;
begin
Result := a;
SetLength(Result, Length(Result));
end;

–jeroen

Posted in Delphi, Development, Software Development | 1 Comment »

git – Change commit author at one specific commit – Stack Overflow

Posted by jpluimers on 2020/09/22

Every now and then I forget to git config --local user.name and git config --local user.email, so git takes my global settings and I need to fix one or more commits to it shows the correct author.

For the last commit, when not yet pushed, this is easy:

git commit --amend --author="Author Name <email@address.com>"

For historic commits, or when you already pushed, it gets far more difficult, so I am glad there is a good set of steps at [WayBackgit – Change commit author at one specific commit – Stack Overflow.

For now in my %USERPROFILE%\.gitconfig file, I have added entries for various accounts so it is easier to spot them with git config --list --global then edit them using git config --edit --local:

[user.foo]
    name = jeroenfo
    email = ########+jeroenfoo@users.noreply.github.com
[user.gh]
    name = Jeroen Wiert Pluimers
    email = jeroen.vvv.www@pluimers.com
[user.gl]
    name = Jeroen Wiert Pluimers
    email = jeroen.xxx.yyy@pluimers.com

If you pushed, but nobody pulled, and you are the only one committing, then the steps are like this if your git is 1.8 or higher:

  1. Once,
    1. perform git rebase -i --root
    2. at all commits you want to edit, change pick into edit
    3. write the file, then leave the editor (:wq)
  2. For each commit, until git indicates No rebase in progress?:
    1. perform git commit --amend --reset-author --no-edit
    2. perform git rebase --continue

–jeroen

Posted in Development, DVCS - Distributed Version Control, git, Software Development, Source Code Management | Leave a Comment »

Women should rule IT again, not just because inheritance in Cobol functions differently than in other languages.

Posted by jpluimers on 2020/09/22

From a while back, but still relevant: [WayBack] Vererbung funktioniert in Cobol anders als in anderen Sprachen… – Kristian Köhntopp – Google+

Translated, this is:

I found some COBOL code at a client. Nothing special. The last comment in it was from 1985, written by my mother. That was my WTF moment of the year, including the look on the face of the technical manager: here inheritance gets a totally different perspective.

An interesting take from that thread is that in the past, women ruled IT.

They should do this again while they can, as a mixed team can combine “first time right” with “minimum viable product”. It is all about balance.

Andreas Dorfer
Cool-Programmierung in den 70ern und frühen 80ern scheint eine Frauendomäne gewesen zu sein. Zumindest bei uns waren die letzten Aktiven daran in den späten 90ern (die mehr als nur Hotfixes drangebastelt haben), gestandene Frauen mit Lesebrillen an Perlenketten.

Jeroen Wiert Pluimers
+Andreas Dorfer yup, and they were doing excellent jobs. Women still could rule IT, there are just to few working in IT.

Andreas Dorfer
+Jeroen Wiert Pluimers those folks really listened and asked relevant questions before making any half baked proposal. Then they produced a lot of documents in binders, including flow diagrams… made a prototype, tested the unit and produced another binder full of paper.. And if there any question after going live, they just told you on the phone: “Look at sheet xy, paragraph z, there we documented this behaviour as conforming your request. Shall we schedule a meeting to setup a change request together?”. They had been working like accounting: sometimes incredibly slow, but with precision and accuracy… if things went wrong, the best advice was always to ask yourself, where you might have a flaw in the initial request.

Andreas Dorfer

Archive.is 384da9306d6501301d80001dd8b71c47 (900×266)

This apart from the fact that comments have not changed much over time:

Read the rest of this entry »

Posted in Development, History, Software Development | Leave a Comment »

Delphi Gem of the day: putting “reintroduce” on a destructor. destructor…

Posted by jpluimers on 2020/09/22

A nice thread with examples of all the things you should not do with the Delphi reintroduce keyword:

[WayBack] Delphi Gem of the day: putting “reintroduce” on a destructor.     destructor Destroy(); reintroduce; overload; In our case all we got was a memory lea… – Moz Le – Google+

The problem is that in the original (archived) documentation, not much waring is given around using reintroduce; it is merely posted as solving a nuisance to absolve a compiler warning.

When using it though, all your alarm systems should go off at their highest level as you break polymorphism, but through careful language usage, the pattern you hide can still be used.

One day I will write a longer blog article on this.

Documentation:

A decade of progress has not changed much on this documentation apart from some nicer formatting:

–jeroen

Posted in Conference Topics, Conferences, Delphi, Development, Event, Software Development | Leave a Comment »

7 Rules for Creativity Managers – YouTube

Posted by jpluimers on 2020/09/18

Interesting video explaining there is a lot of work to do around me, meaning I probably need more in stead of less people around me (:

  • Nurture diversity: Creativity managers dislike brains being the same.
  • Create markets: Creativity managers favor coopetition in networks.
  • Rely on merits: Creativity managers embrace networks and gameplay.
  • Make no predictions: Creativity managers keep many options open.
  • Update the workplace: Creativity managers work the environment.
  • Change constraints: Creativity managers optimize for exploration.
  • Open boundaries: Creativity managers connect instead of protect.

Via [WayBack] 7 Rules for Creativity Managers – Marjan Venema – Google+ (who is a great coach).

–jeroen

Read the rest of this entry »

Posted in Agile, Development, LifeHacker, Power User | Leave a Comment »

Delphi: TInvokableClassRegistryHelper.GetInterfaceNamespace as the opposite of TInvokableClassRegistry.RegisterInterface

Posted by jpluimers on 2020/09/17

A while ago, I needed the opposite of InvRegistry.RegisterInterface(TypeInfo(MySoapInterfacePortType, 'urn:myURN', 'utf-8');, so instead of registering an interface with a namespace URN, obtain the URN by passing the interface inverting [WayBack] TInvokableClassRegistry.RegisterInterface.

This is the class helper I wrote:

type
  TInvokableClassRegistryHelper = class helper for TInvokableClassRegistry
  public
    function GetInterfaceNamespace(Info: PTypeInfo): string;
  end;

function TInvokableClassRegistryHelper.GetInterfaceNamespace(Info: PTypeInfo): string;
var
  InfoGuid: TGUID;
begin
  // call like `Result := InvRegistry.GetInterfaceNamespace(TypeInfo(MySoapInterfaceType));`
  InfoGuid := GetTypeData(Info)^.Guid; // uses TypInfo; see https://stackoverflow.com/questions/8439246/is-it-possible-to-get-the-value-of-a-guid-on-an-interface-using-rtti
  Result := GetNamespaceByGUID(InfoGuid);
end;

It would have been a lot easier if TInvokableClassRegistry.GetIntfIndex has been public, because then [WayBack]TInvokableClassRegistry.GetRegInterfaceEntry could have been used.

–jeroen

Posted in Conference Topics, Conferences, Delphi, Development, Event, SOAP/WebServices, Software Development | Leave a Comment »

FireDAC can do DBMS back-end conditional SQL via Conditional Substitution

Posted by jpluimers on 2020/09/17

Though the field-types mentioned in the problem and solution are equal (so either is wrong), the solution in [WayBackI have a little problem with FireDAC and the TStringField and TWideStringField design time generation… – Juan C. Cilleruelo – Google+ pointed out by Jeff Weir is interesting: FireDAC supports conditionals that depend on the DBMS back-end, so you can differentiate between them.

The feature is called Conditional Substitution and has been present ever since AnyDAC (which got bought by Embarcadero, transformed into FireDAC, then after Idera bought Embarcadero, the main developer got pink-slipped).

The AnyDAC documentation is in the wayback machine, though you have to disable the onload event in order to read it.

The [Archive.is] XE5: Preprocessing Command Text (FireDAC) – RAD Studio documentation is not much different from the current state [Archive.is].

More background reading is at [WayBack] www.freepascal.org/~michael/articles/anydac2/anydac2.pdf and Cary Jensen covered it in his 2017 course on FireDAC of which you can see the free ToC.

Example from that thread:

SELECT ART.CD_ITEM                ,
       ART.CD_FAMILY              ,
       ART.CD_CATALOGUE           ,
       CAT.DS_CATALOGUE           ,
       FAM.DS_FAMILY              ,
{IF MSSQL}
       CASE WHEN EXISTS(SELECT 1 FROM CONFIGURATIONS COM WHERE COM.CD_PARENT = ART.CD_ITEM)
          THEN CAST('Y' AS NVARCHAR) 
          ELSE CAST('N' AS NVARCHAR) 
       END HAS_CONFIGURATION      ,
{fi}
{IF FIREBIRD}
       CASE WHEN EXISTS(SELECT 1 FROM CONFIGURATIONS COM WHERE COM.CD_PARENT = ART.CD_ITEM)
          THEN 'Y'  
          ELSE 'N'  
       END HAS_CONFIGURATION      ,
{fi}
       ART.DS_ITEM                ,
       ART.CD_TAX                 ,
       TAX.DS_TAX                 ,
       TAX.PRC_TAX               ,
...

Given the problem statement, the casts likely should have been VARCHAR instead of NVARCHAR, but the construct can be very powerful.

–jeroen

Posted in Database Development, Delphi, Development, Firebird, InterBase, Software Development, SQL, SQL Server | Leave a Comment »

GitHub – gabr42/MultiBuilder: Runs multiple programs in parallel, shows results

Posted by jpluimers on 2020/09/17

Given a Delphi build-VM with enough CPU cores to run many builds in parallel: [WayBack] GitHub – gabr42/MultiBuilder: Runs multiple programs in parallel, shows results.

Much more on this at [WayBack] The Delphi Geek: Introducing MultiBuilder.

Via: [WayBackParallel build/test systems made easy(er) – Primož Gabrijelčič – Google+

–jeroen

Posted in Delphi, Development, Software Development | Leave a Comment »

A thread written by @SwiftOnSecurity

Posted by jpluimers on 2020/09/16

[WayBack] A thread written by @SwiftOnSecurity:

Corporate purchasing and policies make funding open source Literally Impossible.

Nothing’s going to change until you make them pay you.

Someone filed a bug?
Support contract.

Someone wants a feature?
Support contract.

It’s literally easier to pay you $1500/yr than $25 once.

Edit: since Threader/Threader_app died, I archived the Twitter thread at Archive.today.

And much more: worth a long read.

Via another interesting post: [WayBack] Idea for FOSS projects. Register your project/product name as a trademark and only use it for official, stable releases. Have a different name for your … – Jan Wildeboer – Google+

Idea for FOSS projects. Register your project/product name as a trademark and only use it for official, stable releases. Have a different name for your not-(yet)-stable Code.

Put trademark agreements in place. Everyone who uses your trademarked name for services based on your code has to pay. Everybody using the non-stable code is free to do so, but cannot use your trademarked name.

With lots of interesting comments:

  • Jan Wildeboer
    +Andreas Kahler because when you don’t allow use without pay you are violating the open source principles.
  • You just don’t allow the use of the trademarks. That’s perfectly fine with FOSS, e.g. with GPLv3: “you may […] supplement the terms of this License with terms: […] Declining to grant rights under trademark law for use of some trade names, trademarks, or service marks”. See opensource.google.com – Trademarks in Open Source – opensource.google.com
  • +Andreas Kahler Yep. That’s how we work at Red Hat ;)
  • It’s how most distros work – it can be a problem though because you then control how the mark is used and without care it becomes a blocker. Eg it’s really hard to ship Unbuntu based stuff because you can’t modify Ubuntu and call it Ubuntu (which is fair enough) , but for cloud images – problem.
  • +Alan Cox That’s why it IMHO makes more sense for projects/products.
  • Jan Wildeboer+1
    +Torsten Kleinz … Setting up a new provider at any medium to big company is a big, lengthy and horrifyingly complex process.

–jeroen

Read the rest of this entry »

Posted in Development, Open Source, Software Development | Leave a Comment »

Not to self: ERROR_ALREADY_EXIST (183) can also mean your named Mutex already exists

Posted by jpluimers on 2020/09/16

A while ago, I had an error like this when debugging plugins:

Project bds.exe raised exception class EOSError with message ‘System Error.  Code: 183.
Cannot create a file when that file already exists’.

It got was raised when [WayBackGetLastError returned ERROR_ALREADY_EXIST which according to [WayBackSystem Error Codes (0-499) (Windows) has this description:

ERROR_ALREADY_EXISTS

183 (0xB7)
Cannot create a file when that file already exists.

 

The last line is the same description that [WayBackFormatMessage returns. And it put me on the wrong foot as it wasn’t a file, but a mutex that was created: indeed [WayBackCreateMutex documents it:

If the mutex is a named mutex and the object existed before this function call, the return value is a handle to the existing object, GetLastError returns ERROR_ALREADY_EXISTS, bInitialOwner is ignored, and the calling thread is not granted ownership. However, if the caller has limited access rights, the function will fail with ERROR_ACCESS_DENIED and the caller should use the OpenMutex function.

In the mean time, the plugin doesn’t raise that as an exception any more.

–jeroen

 

Posted in Development, Software Development, Windows Development | Leave a Comment »