Это решение работает, выясняя, подключен ли текущий терминал к серверу tmux, работающему на той же машине. Чтобы выяснить связь, мы будем использовать псевдотерминальную пару и хакерскую статистику .
Однако может произойти сбой, если файлы /proc
fs или /dev
недоступны для чтения / записи пользователем. Например, если tmux-сервер был запущен пользователем root, пользователь без полномочий root не сможет его найти.
Кроме того, мы можем получить ложные срабатывания, если сервер tmux получает данные из какого-то другого источника, в то время как мы пытаемся записать в него нули.
Поместите это в конец .bashrc
или другого файла запуска оболочки, который вы хотите:
# ~/.bashrc
# don't waste time if $TMUX environemnt variable is set
[ -z $TMUX ] || return
# don't start a tmux session if current shell is not connected to a terminal
pts=$(tty) || return
# find out processes connected to master pseudoterminal
for ptm in $(fuser /dev/ptmx 2>/dev/null)
do
# ignore process if it's not a tmux server
grep -q tmux /proc/$ptm/comm || continue
# number of bytes already read by tmux server
rchar_old=$(awk '/rchar/ {print $2}' /proc/$ptm/io)
# write out 1000 bytes to current slave pseudoterminal terminal
dd bs=1 count=1000 if=/dev/zero of=$pts &>/dev/null
# read number of bytes again and find difference
diff=$(( $(awk '/rchar/ {print $2}' /proc/$ptm/io) - rchar_old ))
# if it equals 1000, current terminal is connected to tmux server
# however diff comes greater than 1000 most of the times
[ $diff -ge 1000 ] && return
done
# start or attach to a tmux session
echo 'Press any key to interrupt tmux session.'
read -st1 key && return
# connect to a detached session if exists for current user
session=($(tmux list-sessions 2>/dev/null | sed -n '/(attached)/!s/:.*r//p'))
[ -z $session ] || exec tmux a -t ${session[0]}
# start a new session after all
exec tmux
Основной вопрос здесь то, что XmlSerializer
вызовы WriteEndElement()
на XmlWriter
когда это записало бы конечный тэг. Это, однако, генерирует стенографию <tag/>
сформируйтесь, когда не будет никакого содержания. WriteFullEndElement()
пишет конечный тэг отдельно.
Можно ввести собственное XmlTextWriter
в середину, которую сериализатор затем использовал бы для показа той функциональности.
Учитывая, что serializer
соответствующее XmlSerializer
, попробуйте это:
public class XmlTextWriterFull : XmlTextWriter
{
public XmlTextWriterFull(TextWriter sink) : base(sink) { }
public override void WriteEndElement()
{
base.WriteFullEndElement();
}
}
...
var writer = new XmlTextWriterFull(innerwriter);
serializer.Serialize(writer, obj);
[Редактирование] для случая Вашего добавленного кода, добавляют конструкторы фасада для:
public XmlTextWriterFull(Stream stream, Encoding enc) : base(stream, enc) { }
public XmlTextWriterFull(String str, Encoding enc) : base(str, enc) { }
Затем используйте поток памяти в качестве своего внутреннего потока в конструкторе как прежде:
System.IO.MemoryStream memOut = new System.IO.MemoryStream();
XmlTextWriterFull writer = new XmlTextWriterFull(memOut, Encoding.UTF8Encoding); //Or the encoding of your choice
xmlout.Serialize(writer, envelope, namespc);
Эти два представления являются equiavalent. Почему Вам нужен он для появления в последней форме?
Примечание для записи: OP использовал *** Microsoft. *** Web.Services.SoapEnvelope класс, который является частью чрезвычайно устаревшего продукта WSE 1.0. Этот класс является производным от класса XmlDocument, поэтому возможно, что те же проблемы были бы замечены с XmlDocument.
Ни при каких обстоятельствах не следует использовать WSE для какой-либо новой разработки, и если он уже используется, код следует перенести так скоро, как возможно. WCF или веб-API ASP.NET - единственные технологии, которые следует использовать для веб-служб .NET в будущем.