Работаем с самбой из Java с помощью JCIFS

Tags:

Простые примеры работы с самбой при помощи JCIFS

Ниже показан пример класса для копирования файла на самба-шару и просмотра содержимого заданной шары

import jcifs.Config;
import jcifs.smb.*;
import java.io.*;

public class SambaTest {
  // Нормальный конструктор я тут делать не буду, для тестового примера это не нужно
static final String USER_NAME = "username";
static final String PASSWORD = "password";
static final String DOMAIN = "user_domain";

// Путь к сетевой папке с которой будем работать
static final String NETWORK_FOLDER = "smb://server/share/";


// Копируем файл на шару.
// К сожалению SmbFile ничего не знает о методе copyTo из File,
// так что придется этот метод эмулировать руками. Халява не прокатила :(
// В обратную сторону все тоже самое, только потоки будут в обратную сторону.
public boolean copyFileToSamba(String srcFilePath, String destPath) {
    boolean successful = false;
    try{
        // Создаем объект аутентификатор
        NtlmPasswordAuthentication auth =
          new NtlmPasswordAuthentication(DOMAIN, USER_NAME, PASSWORD);

        // Читаем содержимое исходного файла
        File srcFile = new File(srcFilePath);
        InputStream localFile = new FileInputStream(srcFile);

        // Создаем объект для потока куда мы будем писать наша файл
        SmbFileOutputStream destFileName = new SmbFileOutputStream(
          new SmbFile(destPath+File.separator+srcFile.getName(), auth));

        // Ну и копируем все из исходного потока в поток назначения.
        BufferedReader brl = new BufferedReader(
          new InputStreamReader(localFile));
        String b = null;
        while((b=brl.readLine())!=null){
            destFileName.write(b.getBytes());
        }
        destFileName.flush();


        successful = true;
    } catch (Exception e) {
        successful = false;
        e.printStackTrace();
    }
    return successful;
}

// Читаем
public boolean readShareContent() {
    boolean successful = false;
    try{
        // Создаем объект для аутентификации на шаре
        NtlmPasswordAuthentication auth =
          new NtlmPasswordAuthentication(DOMAIN, USER_NAME, PASSWORD);
        String path = NETWORK_FOLDER;

        // Ресолвим путь назначения в SmbFile
        SmbFile baseDir = new SmbFile(path, auth);

        // Вычитываем все содержимое шары в массив
        SmbFile[] files = baseDir.listFiles();

        // Делаем что-нибудь со списком файлов
        for (int i = 0; i < files.length; i++) {
          SmbFile file = files[i];
          if (file.isDirectory()) {
                System.out.println("Is DIR: "+file.toString());
                continue;
          } else {
                System.out.println("Is FILE: "+file.toString());
          }
        }

        successful = true;
    } catch (Exception e) {
        successful = false;
        e.printStackTrace();
    }
    return successful;
  }
}

Если все работы с шарой невероятно тупят - то нужно сменить режим ресолвинга сервера и шары.

В конструктор добавляем следующее:

Config.setProperty( "jcifs.resolveOrder", "DNS");

Этим мы указываем что ресолвить имя сервера мы будем ТОЛЬКО через DNS. Можно туда добавить всякие NetBIOS и прочее, но на практике я с необходимостью это делать не сталкивался. Естественно, что если у вас в сети нет локального DNS сервера который будет ресолвить именя локальным машин - то механизм надо сменить на другой. Выбор механизмов ресолвинга будет проходить в порядке указанном в конфиге.

Если предполагается копирование больших бинарных файлов, то код копирования надо заменить с:

BufferedReader brl = new BufferedReader(new InputStreamReader(localFile)); String b = null; while((b=brl.readLine())!=null){ destFileName.write(b.getBytes()); }

на:

byte[] buffer = new byte[1024000]; int noOfBytes = 0;

while ((noOfBytes = localFile.read(buffer)) != -1) { destFileName.write(buffer, 0, noOfBytes); }

Если этого не сделать - то большие файлы будут копироваться криво.

Installing and configuring Postgresql 9.4 on Debian 8

Tags:

Install the postgresql server package:

#apt-get install postgresql-9.4

Create cluster (if it haven't created automatically):

#pg_createcluster 9.4 main --start

Next we need to allow connects from remote sources.

Edit /etc/postgresql/9.4/main/postgresql.conf and set listen_addresses to '*'.

Restart the Postgresql service:

#service postgresql Restart

Now we should create database user.

#su postgres
#psql

postgres=# CREATE USER db_user_name WITH PASSWORD 'secret_password';

Create new database and grant access to it to our user.

postgres=# CREATE DATABASE "db_name"
  WITH OWNER "db_user_name"
  ENCODING 'UTF8'
  LC_COLLATE = 'en_US.UTF-8'
  LC_CTYPE = 'en_US.UTF-8'
  TEMPLATE = template0;

Now we have database with UTF8 collation, it is time to allow connect from remote sources. Our user is the owner of the schema.

Edit /etc/postgresql/9.4/main/pg_hba.conf and add line

host    all   db_user_name    0.0.0.0/0               md5

after the line:

host    all   all             127.0.0.1/32            md5

Save file and restart the service.

Now we can connect to our server from remote computer.

git clone recursive

Tags:

В Git 2.6 для Windows появилась неприятная бага - если уровень вложенности сабмодулей больше 3х, то команда git clone --recursive падает с ошибкой при клонировании глубоко вложенных сабмодулей.

Как бороться - разбить клонирование на 3 этапа:

git clone <repo_addr>
cd <repo_dir>
git submodule update --init
git submodule foreach --recursive git submodule update --init

Здесь мы просто клонируем репозиторий, при необходимости можно сделать чекаут на нужную ветку. Затем инициализируем и загружаем сабмодули первого уровня. И последняя команда проходит рекурсивно по всем сабмодулям рекурсивно и загружает их на неограниченном (наверное) уровне вложенности.

State переменные в Perl

Tags:

В Perl существует особый тип переменных под названием state.

В доке про них написано:

state declares a lexically scoped variable, just like my. However, those variables will never be reinitialized ...

На первый взгляд это дает нам возможность очень просто реализовывать счетчики и иже с ними:

sub count {
  state $count = 0;
  $count++;
}

Однако, есть нюанс - фраза will never be reinitialized означает что переменная действительно никогда не будет переинициализирована пока существует родительский скрипт. И это дает нам вот такую замечательную граблю на которую можно ненароком наступить:

Объявляем пакет:

package MyTestState;

use strict;
use feature 'state';

sub new {
  bless {}, shift;
}

sub count {
  state $count = 0;
  $count++;
}

1;

И саму программу:

use lib 'lib';
use v5.18;
use MyTestState;

my $mystate =  MyTestState->new();

for (0..10) {
  my $counter = $mystate->count();
  say "Counter [$counter]";
}

Вывод ожидаем:

Counter [0]
Counter [1]
Counter [2]
...
Counter [10]

А теперь добавляем такой код:

undef $mystate;

say "next object!=======";

my $mystate1 = MyTestState->new();
for (0..10) {
  my $counter = $mystate1->count();
  say "Counter [$counter]";

}

Здесь мы удаляем старый объект со счетчиком и создаем новый. Логично предположить что счетчик пойдет заново, но на самом деле нет. Не смотря на то что мы удалили старый объект и создали новый, переменная со счетчиком никуда не делась и не была переиницализирована! И при запуске программы мы увидим:

Counter [0]
Counter [1]
Counter [2]
...
Counter [10]
next object!
Counter [11]
Counter [12]
Counter [13]
...
Counter [20]
Counter [21]

Так что слово newer в документации действительно значит "никогда пока жив инстанс интерпретатора запустивший скрипт".

Spotlight does not search for

Tags:

If your Spotlight does not search for some files or applications:

The first of all - restart the Spotlight:

sudo launchctl unload -w /System/Library/LaunchDaemons/com.apple.metadata.mds.plist
sudo launchctl load -w /System/Library/LaunchDaemons/com.apple.metadata.mds.plist

If it have no effect - remove Spotlight's index:

Stop Spotlight service:

sudo launchctl unload -w /System/Library/LaunchDaemons/com.apple.metadata.mds.plist

Remove Spotlight index folder:

sudo rm -rf /.Spotlight-V100

Run service:

sudo launchctl load -w /System/Library/LaunchDaemons/com.apple.metadata.mds.plist

After reindex - everything should work well.

Яндекс.Метрика