czwartek, 18 grudnia 2014

How maven resolves dependencies - raw draft

Package: org.apache.maven.project.DefaultProjectDependenciesResolver.java Method: resolve(DependencyResolutionRequest request)
public interface DependencyResolutionRequest {
 MavenProject getMavenProject();
 DependencyResolutionRequest setMavenProject( MavenProject project );
 DependencyFilter getResolutionFilter();
 DependencyResolutionRequest setResolutionFilter( DependencyFilter filter );
 RepositorySystemSession getRepositorySession();
 DependencyResolutionRequest setRepositorySession( RepositorySystemSession repositorySession );
}
public class DefaultDependencyResolutionRequest
    implements DependencyResolutionRequest
  public DependencyResolutionResult resolve( DependencyResolutionRequest request )
        throws DependencyResolutionException
    {
        RequestTrace trace = RequestTrace.newChild( null, request );

        DefaultDependencyResolutionResult result = new DefaultDependencyResolutionResult();

        MavenProject project = request.getMavenProject();
        RepositorySystemSession session = request.getRepositorySession();
        if ( logger.isDebugEnabled()
            && session.getConfigProperties().get( DependencyManagerUtils.CONFIG_PROP_VERBOSE ) == null )
        {
            DefaultRepositorySystemSession verbose = new DefaultRepositorySystemSession( session );
            verbose.setConfigProperty( DependencyManagerUtils.CONFIG_PROP_VERBOSE, Boolean.TRUE );
            session = verbose;
        }
        DependencyFilter filter = request.getResolutionFilter();
In this part there is some initialization done and actually no-magic.
        ArtifactTypeRegistry stereotypes = session.getArtifactTypeRegistry();

        CollectRequest collect = new CollectRequest();
        collect.setRootArtifact( RepositoryUtils.toArtifact( project.getArtifact() ) );
        collect.setRequestContext( "project" );
        collect.setRepositories( project.getRemoteProjectRepositories() );
If the project has not direct dependencies, the dependencies are taken from the model
        if ( project.getDependencyArtifacts() == null )
        {
            for ( Dependency dependency : project.getDependencies() )
            {
                if ( StringUtils.isEmpty( dependency.getGroupId() ) || StringUtils.isEmpty( dependency.getArtifactId() )
                    || StringUtils.isEmpty( dependency.getVersion() ) )
                {
                    // guard against case where best-effort resolution for invalid models is requested
                    continue;
                }
                collect.addDependency( RepositoryUtils.toDependency( dependency, stereotypes ) );
            }
        }
Otherwise all dependencies are gathered in the map maps dependecies with its versionless id, which will be used for discovering potencial conficts.
        else
        {
            Map dependencies = new HashMap();
            for ( Dependency dependency : project.getDependencies() )
            {
                String classifier = dependency.getClassifier();
                if ( classifier == null )
                {
                    ArtifactType type = stereotypes.get( dependency.getType() );
                    if ( type != null )
                    {
                        classifier = type.getClassifier();
                    }
                }
                String key =
                    ArtifactIdUtils.toVersionlessId( dependency.getGroupId(), dependency.getArtifactId(),
                                                    dependency.getType(), classifier );
                dependencies.put( key, dependency );
            }
            for ( Artifact artifact : project.getDependencyArtifacts() )
            {
                String key = artifact.getDependencyConflictId();
                Dependency dependency = dependencies.get( key );
                Collection exclusions = dependency != null ? dependency.getExclusions() : null;
                org.eclipse.aether.graph.Dependency dep = RepositoryUtils.toDependency( artifact, exclusions );
                if ( !JavaScopes.SYSTEM.equals( dep.getScope() ) && dep.getArtifact().getFile() != null )
                {
                    // enable re-resolution
                    org.eclipse.aether.artifact.Artifact art = dep.getArtifact();
                    art = art.setFile( null ).setVersion( art.getBaseVersion() );
                    dep = dep.setArtifact( art );
                }
                collect.addDependency( dep );
            }
        }
Now is time for adding managed dependencies (WTF..)
        DependencyManagement depMngt = project.getDependencyManagement();
        if ( depMngt != null )
        {
            for ( Dependency dependency : depMngt.getDependencies() )
            {
                collect.addManagedDependency( RepositoryUtils.toDependency( dependency, stereotypes ) );
            }
        }

Extras

Btw. list of stereotypes:
 default
 ear
 eclipse-application
 eclipse-feature
 eclipse-plugin
 eclipse-repository
 eclipse-target-definition
 eclipse-test-plugin
 eclipse-update-site
 ejb
 ejb3
 ejb-client
 jar
 javadoc
 java-source
 maven-plugin
 par
 pom
 rar
 test-jar
 war

Resolving list of artifacts

Location: org.eclipse.aether.internal.impl.DefaultArtifactResolver.java:242
 public List resolveArtifacts( RepositorySystemSession session,
                                                  Collection requests )
{
        SyncContext syncContext = syncContextFactory.newInstance( session, false );

        try
        {
            Collection artifacts = new ArrayList( requests.size() );
            for ( ArtifactRequest request : requests )
            {
                if ( request.getArtifact().getProperty( ArtifactProperties.LOCAL_PATH, null ) != null )
                {
                    continue;
                }
                artifacts.add( request.getArtifact() );
            }

            syncContext.acquire( artifacts, null );

            return resolve( session, requests );
        }
        finally
        {
            syncContext.close();
        }
    }

ReactorReader

Find file appropriate for given Artifact in local reactor
public File findArtifact( Artifact artifact )

poniedziałek, 27 października 2014

log4j 1.x - How appending log messages works - deep dive

All source code listings comes from 1.2.17

Once Logger.info(String) invoked there is the following implementation underneath

// org.apache.log4j.Category
661  public
662  void info(Object message) {
663    if(repository.isDisabled(Level.INFO_INT))
664      return;
665    if(Level.INFO.isGreaterOrEqual(this.getEffectiveLevel()))
666      forcedLog(FQCN, Level.INFO, message, null);
667  }
The repository object is of Hierarchy type which is specialized in retrieving loggers by name and maintaining hierarchy of loggers. FQCN - is fully qualified name of the calling category class After couple of self-explanatory checks we've got forcedLog(String,Priority,Object,Throwable) method called which creates a new logging event and call the appenders.
//org.apache.log4j.Category
389  protected
390  void forcedLog(String fqcn, Priority level, Object message, Throwable t) {
391    callAppenders(new LoggingEvent(fqcn, this, level, message, t));
392  }
At this point lets stop a while with LoggingEvent object. The LoggingEvent is a container object gathering calling category class name, actual message, optional throwable and timestamp. Timestamp can be passed in to the constructor, or is initialized with System.currentTimeMillis() during creation. It will be used by appenders for various reasons before eventually get them logged (eg. filtering). The loggingEvent is passed to callAppenders method:
//org.apache.log4j.Category
198 public
199  void callAppenders(LoggingEvent event) {
200    int writes = 0;
201
202    for(Category c = this; c != null; c=c.parent) {
203      // Protected against simultaneous call to addAppender, removeAppender,...
204      synchronized(c) {
205 if(c.aai != null) {
206   writes += c.aai.appendLoopOnAppenders(event);
207 }
208 if(!c.additive) {
209   break;
210 }
211      }
212    }
213
214    if(writes == 0) {
215      repository.emitNoAppenderWarning(this);
216    }
217  }
It goes through all the parent categories (loggers) ending with RootLogger inherently having no parent. Usually the root logger is the one having appenders. Field aai (of AppenderAttachableImpl type) is used to kept list of appenders.
// org.apache.log4j.helpers.AppenderAttachableImpl
57  public
58  int appendLoopOnAppenders(LoggingEvent event) {
59    int size = 0;
60    Appender appender;
61
62    if(appenderList != null) {
63      size = appenderList.size();
64      for(int i = 0; i < size; i++) {
65 appender = (Appender) appenderList.elementAt(i);
66 appender.doAppend(event);
67     }
68   }    
69   return size;
70  }
That is all from the core side. Now the actual appenders goes into play.

wtorek, 7 października 2014

Ubuntu 14.04 and Eclipse - how to change black tooltip background with light yellow

If you are using the default Ambience theme there are couple of config files you need to modify for changing the black tooltip color with the lightyellow one. First lets identify file where background is defined:
$ grep -R "tooltip_bg_color" /usr/share/themes/Ambiance
you should be output with the following
/usr/share/themes/Ambiance/gtk-3.0/settings.ini:gtk-color-scheme = "base_color:#ffffff\nbg_color:#f2f1f0\ntooltip_bg_color:#000000\nselected_bg_color:#f07746\ntext_color:#3C3C3C\nfg_color:#4c4c4c\ntooltip_fg_color:#ffffff\nselected_fg_color:#ffffff\nlink_color:#DD4814\nbg_color_dark:#3c3b37\nfg_color_dark:#dfdbd2"
/usr/share/themes/Ambiance/gtk-3.0/gtk-main.css:@define-color tooltip_bg_color #f5f5b5;
/usr/share/themes/Ambiance/gtk-3.0/gtk-widgets.css:                                     from (alpha (mix (@tooltip_bg_color, #ffffff, 0.2), 0.86)),
/usr/share/themes/Ambiance/gtk-3.0/gtk-widgets.css:                                     to (alpha (@tooltip_bg_color, 0.86)));
/usr/share/themes/Ambiance/gtk-2.0/gtkrc:gtk-color-scheme = "base_color:#ffffff\nfg_color:#4c4c4c\ntooltip_fg_color:#000000\nselected_bg_color:#f07746\nselected_fg_color:#FFFFFF\ntext_color:#3C3C3C\nbg_color:#F2F1F0\ntooltip_bg_color:#f5f5b5\nlink_color:#DD4814"
/usr/share/themes/Ambiance/gtk-2.0/gtkrc: bg[NORMAL]        = @tooltip_bg_color
/usr/share/themes/Ambiance/gtk-2.0/gtkrc: bg[SELECTED]      = @tooltip_bg_color
We are interested with
  • /usr/share/themes/Ambiance/gtk-3.0/settings.ini
  • /usr/share/themes/Ambiance/gtk-3.0/gtk-main.css

Now lets replace
tooltip_bg_color:#000000 with tooltip_bg_color:#f5f5b5, and
tooltip_fg_color:#ffffff with tooltip_fg_color:#000000

$ sudo sed -i 's/tooltip_bg_color:#000000/tooltip_bg_color:#f5f5bf/' /usr/share/themes/Ambiance/gtk-3.0/settings.ini
$ sudo sed -i 's/tooltip_fg_color:#ffffff/tooltip_fg_color:#000000/' /usr/share/themes/Ambiance/gtk-3.0/settings.ini
$ sudo sed -i 's/tooltip_bg_color #000000/tooltip_bg_color #f5f5b50/' /usr/share/themes/Ambiance/gtk-3.0/gtk-main.css
$ sudo sed -i 's/tooltip_bg_color #ffffff/tooltip_bg_color #000000/' /usr/share/themes/Ambiance/gtk-3.0/gtk-main.css
Finally you need to change theme to some other and back to Ambience and after that full restart of Eclipse is required (soft one (by File->Restart) may be not enough).

piątek, 29 sierpnia 2014

Quick way of installing groovy without root priviliges

And quick one-liner
mvn dependency:copy -Dartifact="org.codehaus.groovy:groovy-all:2.3.6" -DoutputDirectory=. && \
_PWD=$PWD && \
groovy() { java -jar ${_PWD}/groovy-all-2.3.6.jar "$@"; }

piątek, 15 sierpnia 2014

How to put OSX symbols like command (⌘), shift (⇧) and others in html document

Once writing the last blog entry I have faced a need of putting OSX symbols in it. After looking around I found some:
  • &#8679; (⇧) shift
  • &#8963; (⌃) ctrl
  • &#8984; (⌘) command
  • &#8997; (⌥) option
  • &#8677; (⇥) tab
  • &#9099; (⎋) escape
  • &#63743; () apple - only on Macs

OSX 10.9.x Mavericks - how to make eclipse shortcut command + comma works properly (or more precisely - how to change shortcut for "Preferences..." menu option)

Actually there is nothing wrong with the default one ⌘, - unless you are Eclipse user extensivly using "Next/Previous Annotation" and comes from Windows/Linux world :>. In such a case you encounter weird shortcuts ⌘. for "next" and ⇧⌘. for "previous". This is at least unnatural (esspecially for my fingers :)).

Ok, usually when you'd like to change any keyboard shortcut you press ⌃F2, open System Preferences..., type "Keyboard shortcuts" - but looking back and forward through all the categories you are not able to found "Preferences..." one. The solution is to go to the last one category - "App Shortcuts". Once done under box on the right two little buttons should appear [+][-] - click on the [+]. In "Menu Title" text box type "Preferences...", and put new shortcut (eg. ⇧⌘,). Now old shortcut is freed.

Now as we have ⌘, freed, we can assign it to "Previous" command in Eclipse. To do this go the the Eclipse -> Preferences (you can use newly set shortcut ;)) -> General -> Keys -> type "Previous" and replace the shortcut.

poniedziałek, 28 lipca 2014

How to implement onSelectionChange listener on CTabItem tabs of the CTabFolder widget

On the first glance there is no easy way for running arbitrary piece of code once one of the CTabItem tab is changed. Lucky there is generic addListener(int eventType, Listener listener) delivered with Widget class.
CTabItem item = new CTabItem(tabFolder, SWT.NULL);
item.setText(tabTitle);
Composite container = createContent(item.getParent());
item.setControl(container);

item.addListener(SWT.SELECTED, new Listener() {

 @Override
 public void handleEvent(Event event) {
  masterDetailsBlock.setDefaultSelection();
 }
});
But by default there is no such an event notified by CTabFolder. That is why we need take care of it.
tabFolder.addSelectionListener(new SelectionAdapter() {
 @Override
 public void widgetSelected(SelectionEvent e) {
  tabFolder.getSelection().notifyListeners(SWT.SELECTED, new Event());
 }
});
Thats all. Works like a charm ;)

czwartek, 3 lipca 2014

Docker howto - most useful commands with examples

Docker commands

Most basic commands:

docker pull ubuntu 
- downloads image from Docker repository
docker ps -a
- shows all available containers
docker ps -as
- shows all containers with the actual size of the rw-layer
docker ps -lq
- finds out container id of the last started container

How to remove all containers which name or image matches specified regular expression

  for i in $(docker ps -a | grep "REGEXP_PATTERN" | cut -f1 -d" "); do echo $i; done

Note that this command does not filter containers on any particular field - there is no difference if pattern is found on container name, image name, or any other field.

How to run bash on running container

  docker exec -ti ceb1be03097d /bin/bash

How to create image based on container

  docker commit ceb1be03097d /:

Dockerfile

How to change password to the root user?

RUN echo 'root:my_password' |chpasswd

Troubleshooting

$ docker ps
FATA[0000] Get http:///var/run/docker.sock/v1.16/containers/json: dial unix /var/run/docker.sock: permission denied. Are you trying to connect to a TLS-enabled daemon without TLS?

Try the following: $ sudo docker ps

środa, 4 czerwca 2014

Binding key strokes to eclipse commands

The key is specified as uppercased character. However, there can be also specified other keys, which can be also no printable.
The following special literals are available :
  • SPACE, TAB, CR, DEL, ESC, BREAK, BS, CAPS_LOCK, END, HOME, INSERT, PAGE_UP, PAGE_DOWN
  • ARROW_DOWN, ARROW_LEFT, ARROW_RIGHT, ARROW_UP
  • F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, F11, F12, F13, F14, F15, FF
  • NUM_LOCK, NUMPAD_0, NUMPAD_1, NUMPAD_2, NUMPAD_3, NUMPAD_4, NUMPAD_5, NUMPAD_6, NUMPAD_7, NUMPAD_8, NUMPAD_9, NUMPAD_ADD, NUMPAD_DECIMAL, NUMPAD_DIVIDE, NUMPAD_ENTER, NUMPAD_EQUAL, NUMPAD_MULTIPLY, NUMPAD_SUBTRACT
  • LF, NUL, , PAUSE, PRINT_SCREEN, SCROLL_LOCK, and VT

poniedziałek, 12 maja 2014

How to lock IntelliJ IDEA on Unity launcher

Most straightforward way is running the IntelliJ from command line and once opened "right click" on icon appeared on the launcher and click "Lock to Launcher".

Now you can go to terminal (Ctrl+Atl+T) and edit newly created desktop file ~/.local/share/applications/jetbrains-idea-ce.desktop

The key point is to fix Exec entry - should be path to the ./idea.sh start script. Note that if you have not JAVA_HOME set in your environment, you need set one as shown below.
[Desktop Entry]
Encoding=UTF-8
Version=1.0
Type=Application
Name=IntelliJ IDEA
Icon=jetbrains-idea-ce.png
Path=/home/krma/Downloads/idea-IC-135.690/bin
Exec=env JAVA_HOME=/usr/lib/jvm/java-8-oracle /home/krma/Downloads/idea-IC-135.690/bin/idea.sh
StartupNotify=false
StartupWMClass=jetbrains-idea-ce
OnlyShowIn=Unity;
X-UnityGenerated=true
That is basically all.

czwartek, 8 maja 2014

Eclipse PDE - all about Eclipse Commands

The goal of this site is gather most useful locationURI's one can like to attach custom command for Eclipse environment.

menu:org.eclipse.ui.views.ProblemView
menu:window?after=newEditor
popup:org.eclipse.ui.menus.showInMenu popup:#TextEditorContext?after=copy popup:#TextEditorContext?endof=group.find popup:#TextEditorContext?after=group.open popup:#TextEditorContext?after=group.edit

Useful commands

  • org.eclipse.ui.ide
    • org.eclipse.ui.edit.text.openLocalFile (Open a local file)
    • org.eclipse.ui.navigate.goToResource (Go to particulare resource in the active window)
    • org.eclipse.ui.navigate.openResource (Open an editor on a praticular resource)
      • handler: org.eclipse.ui.internal.ide.handlers.OpenResourceHandler
      • param: filePath
    • org.eclipse.ui.edit.addTask (Add a task)
      • defaultHandler:  no
    • org.eclipse.jdt.ui.edit.text.java.correction.assist.proposals (Suggest possible fixes for a problem)
      • deafultHander: no
    • org.eclipse.ui.navigate.showResourceByPath (Show a resource in the Navigator given its path)
      • defaultHandler: org.eclipse.ui.internal.ide.handlers.ShowResourceByPathHandler
      • resourcePath
    • org.eclipse.ui.ide.copyBuildIdCommand (Copies the build id to the clipboard)
      • defaultHandler: org.eclipse.ui.internal.ide.commands.CopyBuildIdToClipboardHandler
  • org.eclipse.ui
    • org.eclipse.ui.newWizard (Open wizard)
      • param: newWizardId
    • org.eclipse.ui.file.import
      • param:  importWizardId
    • org.eclipse.ui.file.export
      • param: exportWizardId

Invoke programmatically

ICommandService commandService = (ICommandService) PlatformUI.getWorkbench()
                .getActiveWorkbenchWindow().getService(ICommandService.class);

IEvaluationService evaluationService = (IEvaluationService) PlatformUI.getWorkbench()
                .getActiveWorkbenchWindow().getService(IEvaluationService.class);
try {
 Command c = commandService.getCommand("org.eclipse.ui.newWizard");

 Map<String, String> params = new HashMap<String, String>();
 params.put("newWizardId", "mywizard.id");

 c.executeWithChecks(new ExecutionEvent(c, params, null, evaluationService.getCurrentState()));

} catch (Exception ex) {
 throw new RuntimeException("Open new wizard command not found");
}

 Menus


   
      
         
             
             
             
             
         
      
   



   
      
         
           
         
      
      
        
      
   



   
      
      
         
            
            
         
      
   



   


wtorek, 6 maja 2014

Ubuntu 14.04 - How to dock applications to the Unity launcher

There is a gsettings command which let us do the job.

First we need to retrieve current configuration.

gsettings get com.canonical.Unity.Launcher favorites

We should receive something like that:

['application://nautilus.desktop', 'application://firefox.desktop', 'application://ubuntu-software-center.desktop', 'application://unity-control-center.desktop', 'unity://running-apps', 'application://eclipse.desktop', 'unity://expo-icon', 'unity://devices']

Now we need to put our application (luna.desktop entry - should be created manually in well-known applications folder - eg. ~/.local/share/applications/luna.desktop)

gsettings set com.canonical.Unity.Launcher favorites ['application://nautilus.desktop', 'application://firefox.desktop', 'application://ubuntu-software-center.desktop', 'application://unity-control-center.desktop', 'unity://running-apps', 'application://eclipse.desktop', 'application://luna.desktop', 'unity://expo-icon', 'unity://devices']

New launcher item will appear immediately.