Перейти к содержимому


Фотография

TSR mail или элементарная почта с пересылкой файлов

OC mail send file tsr

  • Авторизуйтесь для ответа в теме
Сообщений в теме: 21

#1 Оффлайн   swg2you

swg2you
  • Пользователи
  • Сообщений: 268
  • Уровень сигнала: 0%
  • В игре: 0 час. 0 мин.

Награды

              

Отправлено 24 Июнь 2015 - 00:39

Модуль отправки: send.lua

print('Use: send [<receiver-address>] < <filename> - for send filename,\nor: send [<receiver-address>] - for write, and Ctrl+C to send.')
local port = 9
local c = require("component")
local m = c.proxy(c.list("modem")())
local s, addr = io.read("*a"), ...
if #s>0 then
  if addr then m.send(addr, port, s)
  else m.broadcast(port, s) end
  print('Sended: '..#s..' bytes')
end

и резидентный модуль приема: tsrmail.lua

local port = 9
if _tsrmail then
  print('tsrmail already loaded @ port '.._tsrmail)
else
  local beep=0
  local c = require("component")
  local cp = require("computer")
  local fs = require("filesystem")
  local m=c.proxy(c.list("modem")())
  local pullSignal = cp.pullSignal
  cp.pullSignal = function (...)
    local e={pullSignal(...)}
    if e[1]=='modem_message' then 
      local h = fs.open('@','a')	
      h:write('--'..os.date()..' From:'..e[3]..'\n'..table.concat({table.unpack(e,6)},'\n'))
      h:close()
      beep=1
    elseif e[1]=='key_down' then
      beep=0
    elseif beep>0 then 
      cp.beep(440) 
    end
    beep=-beep
    return table.unpack(e)
  end
  m.open(port)
  print('tsrmail loaded @ port '..port)
  _G._tsrmail=port
end

сохранить на диск.

tsrmail.lua - запустить, после чего она останется резидентным модулем в памяти, и слушая 9-й порт, будет складывать всю почту в файл "@" на диске.

 

Пример использования:

 

У пользователя Коли, и еще у кого-то, есть компьютер с сетевой картой, на котором работает резидентная tsrmail.lua.

 

Программист Вася только что, получил на дискетке копию "TSR mail", запустил  tsrmail.lua, чтобы иметь возможность принимать почту, и ему не терпится заявить о себе всему миру. Он запускает send, читает две строчки справки, пишет пару строк сообщения (хеловорд конечно, что же еще может написать программист) и нажав Ctrl+C отправляет.

h_1435093437_1413607_8e11bbb269.png

 

Но пользователь Коля, как и другие пользователи "TSR mail" заняты своими делами: кормят коров, сажают желтые цветы и воюют с криперами. Хоть Колин компьютер и пищит "хозяин! почта пришла!", Коля далеко и не слышит.

 

Программисту Васе не терпится пообщаться, он хочет чтобы ему тоже прислали что-то. Хоть простенький хелловорд.

 

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

h_1435093438_2556843_da3e02baed.png

 

Пользователь Коля, проходив мимо компьютера, услышал писк и подошел проверить почту. Посмотрев стандартной командой cat @ содержимое файла @, с тремя сообщениями Васи, и пробурчав под нос, - Опять эти программеры фигней страдают, лучше бы коров покормили! - удалил сообщения командой rm @

h_1435093438_8163746_5ffb3896af.png

 

Если бы наш программист догадался прислать что-то поинтереснее, например новую версию пасьянса, то Коля может и сохранил бы его, переименовав mv @ pasians2.lua, и почистив edit pasians2.lua от лишних сообщений.

 

Но к сожалению, это был не пасьянс.

--==--

P.S.

Код quick and dirty, но зато simple and short. По хорошему, нужна обертка-интерфейc для send, которая будет хранить адресную книгу, дополняя адресатов из @, большие файлы пересылать порциями обходя ограничение на размер пакета, красиво показывать @ добавляя функции ответа и сохранения, ну и все такое. А в резидентный модуль неплохо бы добавить отклик "принял".


Сообщение отредактировал swg2you: 24 Июнь 2015 - 04:30

  • Krutoy, Totoro и Fingercomp это нравится

#2 Оффлайн   Krutoy

Krutoy
  • Гуру
  • Сообщений: 499
  • Уровень сигнала: 0%
  • В игре: 0 час. 0 мин.

Награды

              

Отправлено 24 Июнь 2015 - 07:56

Гоу к нам в Opennet http://computercraft...c-prodolzhenie/

Если объеденяться, то твоя программа может сразу появляться у пользователя, а нам пригодятся твои идеи и реализации сетевых алгоритмов. У нас уже и адресная книга aka DNS есть, и пересылка порциями.



#3 Оффлайн   Zer0Galaxy

Zer0Galaxy
  • Гуру
  • Сообщений: 1 228
  • Уровень сигнала: 0%
  • В игре: 0 час. 0 мин.

Награды

   5                              

Отправлено 24 Июнь 2015 - 09:21

и резидентный модуль приема: tsrmail.lua

Так где здесь  пересылка файлов? Эта штука абсолютно весь пойманный эфир (возможно не только 9-й порт) будет сыпать в один файл. И зачем переопределять функцию pullSignal если можно повесить слушателя на событие?



#4 Оффлайн   swg2you

swg2you
  • Автор темы
  • Пользователи
  • Сообщений: 268
  • Уровень сигнала: 0%
  • В игре: 0 час. 0 мин.

Награды

              

Отправлено 24 Июнь 2015 - 11:12

Так где здесь  пересылка файлов? Эта штука абсолютно весь пойманный эфир (возможно не только 9-й порт) будет сыпать в один файл. И зачем переопределять функцию pullSignal если можно повесить слушателя на событие?

Как ты верно подметил, если переименовать tsrmail обратно в tsrsniffer, то мы получим сетевой сниффер, который будет фоном перехватывать все! входящие пакеты на всех! портах и складывать их в файлик. )

Более того, если удалить "=='modem_message'", то мы получим сниффер для всех событий.

upd:
моя не уметь на событие, моя уметь подменять pullSignal

Сообщение отредактировал swg2you: 24 Июнь 2015 - 11:16


#5 Оффлайн   LeshaInc

LeshaInc
  • Пользователи
  • Сообщений: 1 205
  • Уровень сигнала: 15,56%
  • В игре: 116 час. 32 мин.
  • ГородЛуна

Награды

                       

Отправлено 24 Июнь 2015 - 11:21

Через event.listen swg2you можешь повесить слушателя на modem_message. Вот если не знаешь его использование:
Спойлер


#6 Оффлайн   swg2you

swg2you
  • Автор темы
  • Пользователи
  • Сообщений: 268
  • Уровень сигнала: 0%
  • В игре: 0 час. 0 мин.

Награды

              

Отправлено 24 Июнь 2015 - 11:48

Через event.listen swg2you можешь повесить слушателя на modem_message. Вот если не знаешь его использование:

Спойлер

 

Уоу, круто! 

А как это запустить чтоб оно работало в фоне?



#7 Оффлайн   Asummonster

Asummonster
  • Пользователи
  • Сообщений: 570
  • Уровень сигнала: 49,2%
  • В игре: 368 час. 28 мин.
  • ГородКиев

Награды

                    

Отправлено 24 Июнь 2015 - 11:50

Через event.listen swg2you можешь повесить слушателя на modem_message. Вот если не знаешь его использование:

Спойлер

 

Только их там не 6. Если ты напишешь m.broadcast(port, data1)---их будет шесть,а если ты напишешь m.broadcast(port, data1, data2)---их будет 7, и так далее



#8 Оффлайн   swg2you

swg2you
  • Автор темы
  • Пользователи
  • Сообщений: 268
  • Уровень сигнала: 0%
  • В игре: 0 час. 0 мин.

Награды

              

Отправлено 24 Июнь 2015 - 11:50

Гоу к нам в Opennet http://computercraft...c-prodolzhenie/

Если объеденяться, то твоя программа может сразу появляться у пользователя, а нам пригодятся твои идеи и реализации сетевых алгоритмов. У нас уже и адресная книга aka DNS есть, и пересылка порциями.

Я смотрел, но OpenNet пока слишком сложна для моего понимания. Не вижу общей концепции.



#9 Оффлайн   Asummonster

Asummonster
  • Пользователи
  • Сообщений: 570
  • Уровень сигнала: 49,2%
  • В игре: 368 час. 28 мин.
  • ГородКиев

Награды

                    

Отправлено 24 Июнь 2015 - 11:50

Уоу, круто! 

А как это запустить чтоб оно работало в фоне?

Листен всё держит в условном фоне

Ты просто заменяешь event.pull на event.listen(event, function) и всё



#10 Оффлайн   swg2you

swg2you
  • Автор темы
  • Пользователи
  • Сообщений: 268
  • Уровень сигнала: 0%
  • В игре: 0 час. 0 мин.

Награды

              

Отправлено 24 Июнь 2015 - 11:56

Только их там не 6. Если ты напишешь m.broadcast(port, data1)---их будет шесть,а если ты напишешь m.broadcast(port, data1, data2)---их будет 7, и так далее

Это мелочи, мы всегда можем написать
local function listmsg(...)
  print(...)
end
event.listen("modem_message", listmsg)
Главное суметь заставить работать это в фоне. Ждем LeshaInc, чтоб объяснил как это сделать.

Листен всё держит в условном фоне
Ты просто заменяешь event.pull на event.listen(event, function) и всё

т.е. этот код выполнится, оставит слушателя работать, а я смогу тем временем запускать другие программы?

Сообщение отредактировал swg2you: 24 Июнь 2015 - 11:59


#11 Оффлайн   LeshaInc

LeshaInc
  • Пользователи
  • Сообщений: 1 205
  • Уровень сигнала: 15,56%
  • В игре: 116 час. 32 мин.
  • ГородЛуна

Награды

                       

Отправлено 24 Июнь 2015 - 12:09

Покажу на примере как можно в фоне читать сеть.
local event = require("event")
local m     = require("component").modem

m.open(512)

function listener(_,_,_,_,_,msg)
    print(msg)
end
event.listen ("modem_message",listener)
После запуска данного кода в фоне появится некий сниффер, который будет слушать 512 порт и писать все сообщения. Всё будет работать в фоне и ты сможешь, например, запускать любые другие программы.

#12 Онлайн   Fingercomp

Fingercomp
  • Гуру
  • Сообщений: 1 999
  • Уровень сигнала: 170,73%
  • В игре: 1278 час. 43 мин.

Награды

                                               

Отправлено 24 Июнь 2015 - 12:10

Это мелочи, мы всегда можем написать

local function listmsg(...)
  print(...)
end
event.listen("modem_message", listmsg)
Главное суметь заставить работать это в фоне. Ждем LeshaInc, чтоб объяснил как это сделать.

т.е. этот код выполнится, оставит слушателя работать, а я смогу тем временем запускать другие программы?

 

listen слушает "эфир" и выполняет данную функцию при возникновения события данного, опять же. Листенер со всем его содержимым хранятся отдельно от запускаемой программы, и события обрабатываются в фоне. Для удаления листенера необходимо в той же программе вызывать event.ignore(event, func), иначе события будут продолжать обрабатываться даже после завершения программы.



#13 Оффлайн   swg2you

swg2you
  • Автор темы
  • Пользователи
  • Сообщений: 268
  • Уровень сигнала: 0%
  • В игре: 0 час. 0 мин.

Награды

              

Отправлено 24 Июнь 2015 - 12:19

после выполнения этого кода ты сможешь например запускать любые другие программы.

Круто, а как сделать чтобы он не на экран выводил а в файл?

#14 Оффлайн   LeshaInc

LeshaInc
  • Пользователи
  • Сообщений: 1 205
  • Уровень сигнала: 15,56%
  • В игре: 116 час. 32 мин.
  • ГородЛуна

Награды

                       

Отправлено 24 Июнь 2015 - 12:23

Круто, а как сделать чтобы он не на экран выводил а в файл?


Заменить "print(msg)" в моём коде на запись в файл и все.

#15 Оффлайн   swg2you

swg2you
  • Автор темы
  • Пользователи
  • Сообщений: 268
  • Уровень сигнала: 0%
  • В игре: 0 час. 0 мин.

Награды

              

Отправлено 24 Июнь 2015 - 12:29

Заменить "print(msg)" в моём коде на запись в файл и все.

Как именно? Пример будет? Ждем.

Сообщение отредактировал swg2you: 24 Июнь 2015 - 12:29


#16 Оффлайн   Zer0Galaxy

Zer0Galaxy
  • Гуру
  • Сообщений: 1 228
  • Уровень сигнала: 0%
  • В игре: 0 час. 0 мин.

Награды

   5                              

Отправлено 24 Июнь 2015 - 12:44

Как именно? Пример будет? Ждем.

event=require"event"

function listmsg(eventName, receiverAddress, senderAddress, port, distance, ...)
      local h = fs.open('@','a')	
      h:write('--'..os.date()..' From:'..senderAddress..'\n'..table.concat({...},'\n'))
      h:close()
end

event.listen("modem_message", listmsg)

Как то так. Можно еще порт и дистанцию прилепить


Сообщение отредактировал Zer0Galaxy: 24 Июнь 2015 - 12:45


#17 Оффлайн   NEO

NEO
  • Пользователи
  • Сообщений: 1 748
  • Уровень сигнала: 4,86%
  • В игре: 36 час. 25 мин.
  • ГородСолнце

Награды

   3                        

Отправлено 24 Июнь 2015 - 12:47

event=require"event"

function listmsg(eventName, receiverAddress, senderAddress, port, distance, ...)
      local h = fs.open('@','a')	
      h:write('--'..os.date()..' From:'..senderAddress..'\n'..table.concat({...},'\n'))
      h:close()
end

event.listen("modem_message", listmsg)

Как то так. Можно еще порт и дистанцию прилепить

 

лучше io используй.



#18 Онлайн   Fingercomp

Fingercomp
  • Гуру
  • Сообщений: 1 999
  • Уровень сигнала: 170,73%
  • В игре: 1278 час. 43 мин.

Награды

                                               

Отправлено 24 Июнь 2015 - 12:50

Как именно? Пример будет? Ждем.

Достаточно написать функцию-обработчик, типа этого:
 
if _tsrmail then
  print('TSR Mail is already running!')
  return
end
local cp=require'computer'
local com=require'component'
local m=com.modem
local port=9
m.open(port)
function onModemMessageOrKey(eventName, receiverAddr, sender, port, distance, msg)
  if eventName=='modem_message' then
    local h = io.open('/@','a')    
    h:write('--'..os.date()..' From:'..sender..'\n'..table.concat({table.unpack(msg)},'\n'))
    h:close()
    beep=1
  elseif eventName=='key_down' then
    beep=0
  elseif beep>0 then
    cp.beep(440)
  end
  beep=-beep
end

event.listen('modem_message',onModemMessageOrKey)
event.listen('key_down',onModemMessageOrKey)

print('TSR Mail has started!')
_G._tsrmail=port


#19 Оффлайн   swg2you

swg2you
  • Автор темы
  • Пользователи
  • Сообщений: 268
  • Уровень сигнала: 0%
  • В игре: 0 час. 0 мин.

Награды

              

Отправлено 24 Июнь 2015 - 12:58

event=require"event"

function listmsg(eventName, receiverAddress, senderAddress, port, distance, ...)
      local h = fs.open('@','a')	
      h:write('--'..os.date()..' From:'..senderAddress..'\n'..table.concat({...},'\n'))
      h:close()
end

event.listen("modem_message", listmsg)
Как то так. Можно еще порт и дистанцию прилепить

А как сделать, чтобы эта штука сигнализировала пользователю о том, что новое сообщение получено и записано в файл?

#20 Оффлайн   swg2you

swg2you
  • Автор темы
  • Пользователи
  • Сообщений: 268
  • Уровень сигнала: 0%
  • В игре: 0 час. 0 мин.

Награды

              

Отправлено 24 Июнь 2015 - 13:11

Достаточно написать функцию-обработчик, типа этого:

Ох ты, набежали тут, примеров накидали ) я вообще-то с LeshaInc разговаривал ))

Ну ладно, попробуйте event.listen повесить без OpenOS, и на этом закроем тему.

#21 Оффлайн   LeshaInc

LeshaInc
  • Пользователи
  • Сообщений: 1 205
  • Уровень сигнала: 15,56%
  • В игре: 116 час. 32 мин.
  • ГородЛуна

Награды

                       

Отправлено 24 Июнь 2015 - 13:43

А как сделать, чтобы эта штука сигнализировала пользователю о том, что новое сообщение получено и записано в файл?


После h:close можно написать computer.beep.

Ох ты, набежали тут, примеров накидали ) я вообще-то с LeshaInc разговаривал ))Ну ладно, попробуйте event.listen повесить без OpenOS, и на этом закроем тему.


Тут либо делать поток thread, либо через подмену, либо посмотрев реализацию event.listen.

#22 Оффлайн   swg2you

swg2you
  • Автор темы
  • Пользователи
  • Сообщений: 268
  • Уровень сигнала: 0%
  • В игре: 0 час. 0 мин.

Награды

              

Отправлено 24 Июнь 2015 - 14:03

После h:close можно написать computer.beep.

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

Тут либо делать поток thread, либо через подмену, либо посмотрев реализацию event.listen.

Как вариант, внутри обработчика входящих от модема можно повесить новый обработчик по таймеру
local beep=event.timer(1, function() computer.beep(440) end, math.huge)
а снаружи, добавить еще один, который будет слушать клавиатуру и по нажатию на клавишу делать
if beep then event.cancel(beep) end

upd:
Итак, совместные усилия превратились в код нового, хорошего и правильного tsrmail.lua

local port = 9

if _tsrmail then
  io.write('tsrmail already loaded @ port ',_tsrmail)
else
  local beep, cp, ev = false, require("computer"), require("event")
  require("component").modem.open(port)

  local function listener(...)
    local e={...}
    if e[4] == port then
      local h = io.open('@','a')	
      h:write('--', os.date(), ' from:', e[3], ' port:', e[4], '\n')
      h:write(table.concat(e,'\n',6))
      h:close()	
      if not beep then 
        beep=ev.timer(2, function() cp.beep(440) end, math.huge)
      end 
    end
  end

  local function unbeep()
    if beep then 
      ev.cancel(beep)
      beep=false 
    end
  end

  ev.listen("key_down", unbeep)
  ev.listen("modem_message", listener)

  io.write('tsrmail loaded @ port ', port)
  _G._tsrmail=port
end

Спасибо всем оппонентам, кто высказывался по делу:
Zer0Galaxy за, -можно повесить слушателя на событие
LeshaInc за, -покажу на примере
Fingercomp за, -события будут продолжать обрабатываться даже после завершения программы
Zer0Galaxy за, -можно еще порт и дистанцию прилепить
NEO за, -лучше io используй

И всем остальным за общее комментирование и множественные примеры.


Сообщение отредактировал swg2you: 24 Июнь 2015 - 15:43






Темы с аналогичным тегами OC, mail, send file, tsr

Количество пользователей, читающих эту тему: 0

0 пользователей, 0 гостей, 0 анонимных