Как вручную распаковать пакет nuget.

И извлечь из него сборки (библиотеки).

Часто бывает, что нужная библиотека лежит на nuget.org. Если у вас современная Visual Studio, то проблем нет — инструментарий nuget доступен, во всяком случае, из командной строки. Можно установить nuget и отдельно, но что делать, если устанавливать ничего не хочется?

На самом деле пакет nuget (файл *.nuget) это обыкновенный ZIP-архив. Поэтому можно скачать пакет, переименовать его в *.zip и открыть любимым архиватором.

Например, нам нужен упомянутый в предыдущем посте HtmlAgilityPack, версии 1.11.15.

1. Переходим по ссылке https://www.nuget.org/packages/HtmlAgilityPack/1.11.15
2. Выбираем справа Download package
3. Сохраняем пакет
4. Меняем ему расширение на zip
5. Открываем любимым архиватором

В архиве в подкаталоге \lib находятся каталоги различных сборок:

Net20
Net35
Net40
Net40-client
Net45
NetCore45
netstandard1.3
netstandard1.6
netstandard2.0
portable-net45+netcore45+wp8+MonoAndroid+MonoTouch
portable-net45+netcore45+wpa81+wp8+MonoAndroid+MonoTouch
uap10.0

C# Парсер HTML (под .NET Framework 2.0).

Понадобился тут для одного проекта все-таки полноценный парсер HTML, да еще желательно чтоб под не очень свежий .NET Framework 2.0. Ну не хочу я ради небольшого проекта жертвовать совместимостью да и переходить на новый .NET вообще, потому что в старом все прекрасно работает.

В общем выбирал-выбирал и остановился на HtmlAgilityPack, который в версии 1.11.15 поддерживает в т.ч. и .NET 2.0. Версия 1.11.16 .NET 2.0 уже не поддерживает, все остальное, начиная с .NET 3.5 есть.

Скачать можно через NuGet. Как быть тем, у кого NuGet нет читать здесь.

Прямая ссылка
Обсуждение на StackOwerflow

Держаться корней

Чуковский пишет Толстому:
«Лев, знал бы ты, как хочется вот так просто взять и нажраться! Набухаться в хлам, как Есенин. Или нанюхаться, как Маяковский!»
Толстой отвечает:
«Надо держаться, Корней!»

Настройка IPTables на сервере. Часть вторая, с поправками.

Итак, раньше копия мы уже делали первоначальную настройку IPTables, но оказалось, что делали не очень верно.

Товарищ [info]wasserstrahl@ljr внес поправку:

Открытие порта на исходящие соединения.

Ну чтоб с чем-то связаться по определенному порту.

iptables -A INPUT -p tcp —sport <# порта> -j ACCEPT
iptables -A OUTPUT -p tcp —dport <# порта> -j ACCEPT»

Нет.

iptables -A OUTPUT -p tcp —dport <# порта> -j ACCEPT» — это верно вроде,

а «iptables -A INPUT -p tcp —sport <# порта> -j ACCEPT» — нет. Потому что это правило позволяет любой входящий пакет с указанного порта с любого адреса. Если ты хочешь открыть ответы на исходящий трафик, то нужно писать что-то в стиле iptables -A INPUT -p tcp -m state —state RELATED,ESTABLISHED -j ACCEPT

Поправка верная, потому изменяем настройку IPTables в скрипте инициализации сервера.

Удаляем все правила файерволла:

# Delete all rules
echo "Delete firewall rules..."
iptables -F
iptables -F -t nat
iptables -F -t mangle
iptables -X
iptables -t nat -X
iptables -t mangle -X

Устанавливаем основную политику по умолчанию. Запретить все соединения (параноидальный режим):

# Drop all traffic
echo "Set main policy..."
iptables -P INPUT DROP
iptables -P OUTPUT DROP
iptables -P FORWARD DROP

Разрешаем принимать все установленные входящие соединения. Это надо для того, что если мы откроем порт на исходящие соединения, для того, чтоб сервер мог с чем-то связываться (например с WWW или rsync), то ответ был бы принят.

#prinimat' vse ustanovlennye vhodashie soedineniya
echo "Accepts all established inbound connections..."
iptables -A INPUT -m state --state RELATED,ESTABLISHED -j ACCEPT

Открываем порт для клиентов, которые подключаются к серверу по протоколу PPTP (входящий трафик):

#open VPN ports and GRE
echo "Open VPN ports and GRE..."
#to computer
iptables -A INPUT -p tcp --dport 1723 -j ACCEPT
iptables -A OUTPUT -p tcp --sport 1723 -j ACCEPT

И разрешаем для них же протокол GRE:

iptables -A INPUT -p gre -j ACCEPT
iptables -A OUTPUT -p gre -j ACCEPT

Поскольку сам сервер не будет соединяться с VPN-провайдером по протоколу PPTP (есть OpenVPN), то следующие строки я убрал:

iptables -A INPUT -p tcp --sport 1723 -j ACCEPT
iptables -A OUTPUT -p tcp --dport 1723 -j ACCEPT

Разрешаем весь трафик на loopback (lo) интерфейсе. Если у нас будут сервисы, такие как Web-сервер и сервер баз данных MySQL на одном сервере, то связываться они будут как раз через lo-интерфейс.

#accept all traffic an lo interface
echo "Accept all lo interface traffic..."
iptables -A INPUT -i lo -j ACCEPT
iptables -A OUTPUT -o lo -j ACCEPT

Открываем на вход 22 порт (ssh) для клиентов, которые подключатся к серверу через PPTP VPN:

# ssh (22 port)
echo "Open 22 port (ssh) for VPN clients..."
iptables -A INPUT -s 172.16.1.0/24 -p tcp --dport 22 -j ACCEPT
iptables -A OUTPUT -s 172.16.1.0/24 -p tcp --sport 22 -j ACCEPT

Так же разрешаем им доступ к удаленному рабочему столу (XDMCP):

# XDMCP
echo "Open 177 port UDP (XDMCP) for VPN clients..."
iptables -A INPUT -s 172.16.1.0/24 -p udp --dport 177 -j ACCEPT
iptables -A OUTPUT -s 172.16.1.0/24 -p udp --sport 177 -j ACCEPT

echo "Open 6000:6005 ports (Windows XDMCP) in both directions for VPN clients..."
iptables -A INPUT -s 172.16.1.0/24 -p tcp -m multiport --dports 6000:6005 -j ACCEPT
iptables -A OUTPUT -s 172.16.1.0/24 -p tcp -m multiport --sports 6000:6005 -j ACCEPT

iptables -A INPUT -s 172.16.1.0/24 -p tcp -m multiport --sports 6000:6005 -j ACCEPT
iptables -A OUTPUT -s 172.16.1.0/24 -p tcp -m multiport --dports 6000:6005 -j ACCEPT

Разрешаем VPN-клиентам доступ к DNS:

echo "Open DNS for VPN clients..."
iptables -A INPUT -s 172.16.1.0/24 -p udp --dport 53 -j ACCEPT
iptables -A OUTPUT -s 172.16.1.0/24 -p udp --sport 53 -j ACCEPT

iptables -A INPUT -s 172.16.1.0/24 -p tcp --dport 53 -j ACCEPT
iptables -A OUTPUT -s 172.16.1.0/24 -p tcp --sport 53 -j ACCEPT

Разрешаем протокол ICMP (ping):

# Allow ICMP
echo "Allow ICMP and ports for TRACEROUTE..."
iptables -A INPUT -p icmp -j ACCEPT
iptables -A OUTPUT -p icmp -j ACCEPT

И исходящие порты для TRACEROUTE (ответы, входящий трафик уже разрешен командой iptables -A INPUT -m state --state RELATED,ESTABLISHED -j ACCEPT):

#open ports from traceroute
iptables -A OUTPUT -p udp -m multiport --dports 33434:33534 -j ACCEPT

Открываем стандартные порты (HTTP, HTTPS, email, rsync) для доступа к соответствующим сервисам с сервера (входящие):

#Open standart ports (from computer)
echo "Open standart ports (DNS,WWW, email) from server"
# 53-DNS,80 8080/tcp - WWW, 443/tcp - https, 110,443,25,587 - e-mail 873/tcp - rsync (for sbopkg)
iptables -A OUTPUT -p udp -m multiport --dports 53,443 -j ACCEPT
iptables -A OUTPUT -p tcp -m multiport --dports 53,80,8080,443,110,443,25,587,873 -j ACCEPT

Запускаем PPTP VPN сервер (к его настройке вернусь несколько позже):

#start VPN server
echo "Starting PPTD VPN server..."
pptpd &

Производим окончательную настройку файервола для PPTP VPN клиентов:
1. Организуем NAT (маскарадинг):

echo "Final firewall settings for VPN clients..."
#NAT for VPN clients
iptables -t nat -A POSTROUTING -s 172.16.1.0/24 -j MASQUERADE

И немного подправляем пакеты (без этого виснут некоторые соединения). Буду благодарен, если мне кто-нибудь объяснит почему, но кстати, в Ростелекомовском файерволе такая настройка не установлена, потому это плохой провайдер, и их VPN висючий. В свое время задолбался с этим глюком.

#popravlaem pakety (bez etogo visnut nekotorye soedinenia)
iptables -A FORWARD -p tcp -m tcp --tcp-flags SYN,RST SYN -j TCPMSS --clamp-mss-to-pmtu

Скрипт целиком на PasteBin

Источники к сожалению пролюбил.

tinyproxy свалился после обновления

Черт меня дернул обновить tinyproxy, о настройке которого я писал здесь копия

Свалился вот с такой ошибкой:

"Bind" cannot be used with transparent support enabled.
Syntax error on line 37
Unable to parse config file. Not starting.
Not starting (code 70)

Хотя никакое прозрачное проксирование я не включал.

Решилось тем, что строку 37:

Bind <адрес_сервера>

я просто закомментировал. После этого он штатно заработал.

Правда, нифига понять не могу, с чего это вдруг он так странно упал. В прошлой версии все работало, и вроде команда Bind правильная, нужная и на месте.

C#, проверить, открыта ли форма.

Например, для того, чтобы не дать пользователю повторно открыть одно и то же окно, несколько раз.

Например, такой код при нажатии на кнопку создаст столько форм frmChild, сколько раз кнопка будет нажата:

private void btnOpenForm_Click(object sender, EventArgs e)
{
    frmChild fChild = new frmChild();
    fChild.Show();
}

Конечно, можно сделать форму модальной, с помощью fChild.ShowDialog(), тогда мы не будем иметь доступа к первой форме, пока вторая не закроется. Но если это не нужно, например, мы хотим свободно переключаться между двумя формами, но вторую создать только один раз.

Открытые формы содержатся в Application.OpenForms. И фактически, надо просто перебрать этот массив, чтобы посмотреть, открыта или нет форма, например по ее имени:

foreach (Form f in Application.OpenForms)
    {
        if (f.Name == "frmChild")
        {
            lblFormOpened.Text = "Form #2 already opened!";
            return;
        }
    }

Код обработчика нажатия кнопки целиком:

private void btnOpenForm_Click(object sender, EventArgs e)
{
    lblFormOpened.Text = "";
    
    foreach (Form f in Application.OpenForms)
    {
        if (f.Name == "frmChild")
        {
            lblFormOpened.Text = "Form #2 already opened!";
            return;
        }
    }
    frmChild fChild = new frmChild();
    fChild.Show();
}

Источник
Код примера на GitHub

Электроника MK-45

Принесли вот такую няшечку, и оставили на наше попечение.
После замены конденсатора в блоке питания заработал. Показывает факториал из числа 666:

Шильдик:

Да, стоил достаточно дорого, две зарплаты продавца в магазине, или техника на метеостанции. Если примерно советский рубль по покупательной способности считать за евро (а примерно так и выходит), то на наши деньги 125 евро или 9000 путинских рублей. С учетом отсутствия в СССР кредитов, купить его мог профессор или какая-нибудь контора. Минус нашего прибора — даже после чистки клавиш, они все равно периодически залипают, потому подробного видеообзора не будет.
Зато нам едет настоящий программируемый МК, который мог даже в игры — доедет, на него будет полновесный обзор с видео.

Питается от 220 вольт, дисплей вакуумно-люминисцентный (т.е. вместо жидких кристаллов внутри у него хитросделанная вакуумная лампа).

Задняя часть

Микрокалькулятор «Электроника МК-45» является настольным вариантом калькулятора «Электроника МК-36». В настольном варианте не используется клавиша совмещения функций «F», а все функции вынесены в отдельные блоки клавиш. Калькулятор производился с 1983 года на заводах «Эльтав» в Дагестане и на заводе «Электронприбор» в городе Фрязино Московской области и продавался по цене 85 рублей.
Дизайн корпуса калькулятора повторяет модель «Электроника МК-44», однако количество клавиш позволяет легко различить эти модели.
Результат вычисления отображается на четырнадцатиразрядном вакуумно-люминесцентном индикаторе, при этом два разряда[SP1] никак не используются. Это было сделано специально ради экономии, чтобы не изготавливать новую модель индикатора, а использовать уже выпущенную и проверенную.

Калькулятор относится к классу инженерных. Имеются отдельная клавиша для вызова числа пи, клавиши для вычислений с двухуровневыми скобками, клавиши для вычислений тригонометрических функций и логарифмов, а также клавиши перевода величин, выраженных в градусах, в радианы и обратно. Все это значительно упрощало инженерные расчеты с использованием калькулятора.

Питание калькулятора осуществляется от сети переменного тока 220 В.

Габаритные размеры — 241✕185✕77 мм.
Вес не более 1,0 кг.

Описание с elektronika.su

Настройка IPTABLES

На самом деле, жутко не люблю настраивать IPTables, поскольку синтаксис у него несколько инопланетный. Дома и на работе я как-то настроил один раз лет 10 назад и благополучно все забыл. Теперь вот приходится мучительно вспоминать: «Чем ты это делал? Ну вот этой вот мясорубкой.».

Настройки обновлены, старые под катом

Вроде все правильно, но стойкое ощущение, что где-то накосячил. Кто больше шарит в IPTABLES, приму все комментарии по поводу данной темы.

Природо-интернетозащитная песня про Ёлочку

В лесу родилась ёлочка,
В лесу она росла.
Зимой и летом стройная,
Зеленая была.

Метель ей пела песенку:
«Спи, ёлочка, бай-бай!»
А сисадмин на ёлочку
Прикручивал вай-фай

Трусишка зайка серенький
И Леший с Водяным
Собралися под елочкой
С планшетом дорогим.

А кто и с ноутбуками
Под елочку пришел
Здесь нет Роскомнадзора, ведь
Халавный ВэПэЭн!

Везёт лошадка дровенки,
На дровнях — мужичок
А шел бы ты отсюда нах
От ёлки петушок.

И вот уже его бошка
На елочке висит
И наш Darknet Мизулина
Никак, бля, не сломит.

Аццкий погодный информер.

Не, он и правда настолько аццкий и быдлокод, что я всем его даже не покажу. Редкий случай, когда мне почти стыдно. Там все, и наглое выдирание данных прямо из HTML, и стукнутое преобразование их в таблицу, CSV, а потом и DataSet, для дальнейшего анализа, и прочее, и прочее. Если дизайнер изменит сайт, с которого берется погода, то оно работать не будет, и не факт, что я буду это переделывать.

Изначально делалось по очень большой просьбе местных уфологов, плюс для того, чтобы поиграться с управляемым браузером WebKit .NET, который в результате из проекта был выкинут, поскольку оказался не сильно и нужен.

Единственное, что в нем действительно мне нравится — иконка в трее, отображающая последнюю температуру с заданной метеостанции.

В общем, скачать бинарники и исходники можно здесь, а ключик (у кого вдруг еще нет, или кто не из своих захочет на этот быдлокод посмотреть) спрашивать в редакции через Телеграм.

C# Всплывающая форма над областью уведомлений, делаем сами.

Продолжаем разговор о своем окне, всплывающем возле области уведомлений, там где NotifyIcon. Как в тех же мессенджерах при появлении нового сообщения.

На самом деле все оказывается довольно просто, и даже Ктулху вызывать пользоваться WinAPI не надо.

На первом этапе моделируем будущую всплывающую форму. Я, например, создал форму без границ (FormBorderStyle = none), поместил на нее TextBox, который будет отображать сообщение и PictureBox, который будет работать в качестве кнопки закрытия формы.

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

1. Заводим переменные, сохраняющие позиции формы:

private int StartPosX; private int StartPosY;

Ну я еще добавил переменную для сообщения и экспортировал функцию WinAPI, прячущую текстовый курсор:

[System.Runtime.InteropServices.DllImport("user32.dll")]
private static extern bool HideCaret(IntPtr hWnd);
public string MessageText = "";

Плюс настроил в инициализации формы некоторые ее параметры:

public frmPopup()
{
    InitializeComponent();
    //Настройка формы
    this.TopMost = false;
    this.ShowInTaskbar = false;
}

TopMost = false нужен, чтоб форма всплывала из-за области уведомлений, а не загораживала ее собой.

2. Переопределяем обработчик события Load и в нем прячем форму за экран:

protected override void OnLoad(EventArgs e)
{
    //Прячем форму за экран
    StartPosX = Screen.PrimaryScreen.WorkingArea.Width - this.Width;
    StartPosY = Screen.PrimaryScreen.WorkingArea.Height;
    SetDesktopLocation(StartPosX, StartPosY);
    base.OnLoad(e);
    //запуск анимации всплытия
    tmrAni.Interval = 50;
    tmrAni.Start();

}

Туда же можно вставить запуск таймера, который будет анимировать всплытие формы (после base.OnLoad(e)).

Если просто вставить этот код в обработчик события Load, то форма на секунду появится на экране, и будет некрасиво.

3. Далее в обработчиках событий Load и Shown настраиваем нашу форму, например, присваиваем TextBox нужный текст и т.д.

private void frmPopup_Load(object sender, EventArgs e)
{
    //настраиваем TextBox с сообщением
    txtMessage.Height = this.Height - txtMessage.Location.Y - 3;
    txtMessage.Width = this.Width - txtMessage.Location.X - 3;
    txtMessage.BorderStyle = BorderStyle.None;
    txtMessage.BackColor = this.BackColor;
    txtMessage.Text = MessageText;
    txtMessage.ReadOnly = true;
    txtMessage.SelectionStart = 0;

    //и кнопку закрытия
    int CloseX = this.Width - pbClose.Width - 3;
    int CloseY = 3;
    pbClose.Location = new Point(CloseX, CloseY);
}

private void frmPopup_Shown(object sender, EventArgs e)
{
    HideCaret(txtMessage.Handle);
}

3. При каждом срабатывании таймера поднимаем форму на 5 пикселей, а когда форма покажется полностью, то останавливаем таймер и делаем ее «поверх всех окон» (TopMost = true;):

private void tmrAni_Tick(object sender, EventArgs e)
{
    //поднимаем форму на 5 пикселей
    StartPosY -= 5;

    //Если окно видно полностью - останавливаем таймер
    if (StartPosY < Screen.PrimaryScreen.WorkingArea.Height - Height)
    {
        tmrAni.Stop();
        this.TopMost = true;
    }
    else
    {
        SetDesktopLocation(StartPosX, StartPosY);
    }
}

Вот, что получилось:

Код примера целиком

На GitHub

C# Всплывающая форма над областью уведомлений, над NotifyIcon

Спрашивают, как можно сделать всплывающую форму над областью уведомлений, там где «часики» и иконки запущенных в фоне программ. Ну типа как это делается в мессенджерах при получении нового сообщения.

Вот, нашел вам готовый код. Выглядит вполне симпатично.

Можно поиграть с разными опциями, типа эффекта появления и звука при всплытии. Минус — сильно длинный текст отобразить без допиливания не получится.

Потом расскажу, как самому сделать что-то подобное, пусть и не такое симпатичное.

Исходный код

У автора
У меня

Фразочка

Выбросил в фукуяму.

Блин, жалко Лейбов свой генератор заголовков не поддерживает, неплохо бы смотрелось что-то типа: «В ходе зачистки аула Херсов-Мурда лидер Антимиайдана Залдостанов выбросил в фукуяму народного мэра Луганска»

C#, скрыть (убрать) курсор (каретку) из TextBox

Чтоб два раза не вставать, начну сразу с нескольких простейших манипуляций с курсором из TextBox.

Снятие выделения и управление местоположением курсора (каретки)

Иногда текст в многострочном TextBox‘е автоматически выделяется.

И это выделение обычно не нужно. Благо снять его легко, достаточно переместить курсор.

Установка курсора в начало или конец текста

Для установки курсора в начало текста устанавливаем свойство SelectionStart в 0. Т.е. устанавливаем курсор перед первым символом текста:

//ставим курсор в начало текста
txtSampleText.SelectionStart = 0;

Установить курсор в конец текста тоже проблем не представляет:

//ставим курсор в конец текста
txtSampleText.SelectionStart = txtSampleText.Text.Length;

Выделение исчезнет, а курсор будет в начале или конце текста.

Скрытие курсора переводом фокуса

Для того, чтобы визуально скрыть текстовый курсор в TextBox, можно перевести фокус на другой объект формы. Например, далее переведем фокус на кнопку btnClose, находящуюся рядом с TextBox:

//убираем курсор (сменой фокуса на другой элемент формы)
btnClose.Select();

Но смена фокуса иногда влечет за собой нежелательные последствия, например текст нельзя будет прокручивать колесиком мышки. Если нужно, чтобы фокус оставался в TextBox, а каретка (текстовый курсор) не отображалась, стоит воспользоваться WinAPI.

Использование WinAPI для скрытия текстового курсора (каретки)

Сначала экспортируем WinAPI функцию:

public frmHideCaret()
{
    InitializeComponent();
}

[System.Runtime.InteropServices.DllImport("user32.dll")]
private static extern bool HideCaret(IntPtr hWnd);

//...

Потом вызываем ее в обработчике события Shown (если вызвать, например в Load не сработает, надо чтобы форма появилась):

private void frmHideCaret_Shown(object sender, EventArgs e)
{
    HideCaret(txtSampleText.Handle);
}

Весь пример на GitHub

Смотреть в репозитарии

C#. Удаление HTML-тегов из текста.

Т.е. остается только текст между тегами, например из:
<b>жирный текст</b> <a href="http://example.org">Это ссылка куда-то</a>
должно получиться
жирный текст Это ссылка куда-то

Регулярное выражение для HTML-тега

По счастью, оно совсем простое:

<[^>]+>

Пример

Не забываем подключить соответствующее пространство имен:
using System.Text.RegularExpressions;
//...
string htmlText = "<html><head><title>tolik-punkoff.com</title></head> <body>Welcome to Tolik Punkoff blog!</body></html>";
OutputText = Regex.Replace(htmlText, "<[^>]+>", string.Empty);

//Содержимое OutputText:
//tolik-punkoff.com Welcome to Tolik Punkoff blog!

Примечание: В примере между фразами пробелы, потому что есть пробелы между тегами. Функция никаких пробелов сама по себе не вставляет!

EEE PC 2G SURF драйвера и программы

Принесли тут в починку (причем уже второй) такой вот недобук. Убил полдня на него, пришлось делать отдельный дистрибутив XP, из которого было выкинуто почти все лишнее, чтоб влез.

А вот архив для него с родными дровами, софтом и всем прочим. На всякий случай, мало ли кому надо будет.

Скачать с mega.nz