Re: Generics instantiate problems

2020-07-08 Thread mashingan
What I can understand that you need the lib's user should implement their own 
proc implementation right?

Actually tables modules exactly does like that, when the user wants to use a 
specific object as the key, should implement `hash` and `==` so the object can 
be used as key.

It's also catch-able during compile-time.


Re: getFileSize async and sync

2020-06-30 Thread mashingan
It's different because `AsyncFile` keeps its `fd` field private. The Windows 
one is using the version from `winlean` which actually wrapper for 
`GetFileSize` from win32.

Also, windows has peculiarity of different handling whether the file handle is 
synchronous and asynchronous one. That's why it's using the wrapper.


Re: Control mouse in Windows

2020-03-24 Thread mashingan
Most viable option is using [winim](https://github.com/khchen/winim/) and just 
searching on internet how to work with Win32 API.

Another way is using available example in rosetta code [simulating 
keyboard](https://rosettacode.org/wiki/Simulate_input/Keyboard#Nim) and 
add/change some codes to


type
  MouseEvent = enum
meMove = 0x0001
meLeftDown = 0x0002
meLeftUp = 0x0004
meAbsolute = 0x8000

proc initMouse: Input =
  result.`type` = clong itMouse
  var mouse = MouseInput(mouseData: 0, dx: 0, dy: 0,
dwFlags: meAbsolute.culong or meMove.culong)
  result.hwin = InputUnion(mi: mouse)

proc main =
  var mouse = initMouse()
  # set mouse xy pixel position
  mouse.hwin.mi.dx = clong 35_000
  mouse.hwin.mi.dy = clong 35_000
  
  # move it to intended position
  sendInput(1, addr mouse, sizeof(mouse).cint)
  sleep 1000
  
  # flag to press the left mouse button
  mouse.hwin.mi.dwFlags = meAbsolute.culong or meLeftDown.culong or
meLeftUp.culong
  
  # actually pressing the left mouse button
  sendInput(1, addr mouse, sizeof(mouse).cint)

main()

Run


Re: How Seq work with objects ?

2020-03-22 Thread mashingan
> By removing something from the seq it needs to be reordered. ( shift elements 
> )

If you don't need the ordering, use 
[del](https://nim-lang.org/docs/system.html#del%2Cseq%5BT%5D%5BT%5D%2CNatural)

Try the testing by choosing the span element randomly instead of pre-determined 
value. It will ensure compiler couldn't optimize the entire loop-deleting. Or 
from value from program arguments.

Also object (pretty much) possibly allocated on stack while ref allocated in 
heap. Stack allocation is always faster.


Re: examples or documentation of Source Code filters

2020-03-22 Thread mashingan
I used it to generate Golang boilerplate source codes for my last job.


Re: FFI: how to avoid naming arguments in C functions

2020-03-08 Thread mashingan

$ c2nim --header gr.h
gr.h(27, 25) Error: token expected: ;

Run

AFAIK, c2nim cannot read something with c custom macro. You can edit the header 
temporarily to remove that custom macro. In this case it's the `DLLEXPORT`.


Re: Some rant about nim

2020-03-02 Thread mashingan
just a genuine question

> > Not null safe by default

How compiler know whether the data is nil or not if the data for example taken 
from IO? Or is it adding the additional `if thedata == nil` in the code? But 
the checking still done in run-time right?

Or is it just limited to data/object construction?


Re: Why whitespace?

2020-02-18 Thread mashingan
> What other arguments do they have against using tab?

I got this from a tweet, just food for thought:

> Remember, when you are read, you do not know you are dead. It is only painful 
> for others. It's the same when you use tabs and not spaces

;D


Re: How to split stderr/stdout of a subprocess?

2020-01-28 Thread mashingan
The streams implementation on Windows (FileHandleStream to be precise) didn't 
implement peekDataImpl, setPositionImpl and getPositionImpl hence it crashed 
because the streams module accessing nil implementation.

I actually fixed this (not PR-ed it yet tho, maybe already fixed in devel too, 
haven't checked it yet), but the actual problem is another, it's the C buffer 
that wouldn't flush to stdout/stderr handle until the the subprocess' buffer is 
full.


Re: Looking for someone to continue Nimmongo!

2020-01-28 Thread mashingan
[https://github.com/SSPkrolik/nimongo/pull/81](https://github.com/SSPkrolik/nimongo/pull/81)
 there, added for limited elementary functionalities for GridFS.

Unfortunately I never intensively used mongo except for simplest CRUD and those 
GridFS features only tested on Windows, very likely you need to test for Linux 
and/or Bsd variants.

My Mongodb version is 4.0.5


Re: How to split stderr/stdout of a subprocess?

2020-01-21 Thread mashingan
perhaps like this


#include 

int main() {
fprintf(stdout, "This is from hello to stdout\n");
fprintf(stderr, "This is from hello to stderr\n");
return 0;
}


Run

and our nim file


import os, osproc, selectors
when defined(windows):
  import streams

proc main =
  when defined(linux):
let prc = startProcess("./a.out", options = {})
let errh = errorHandle prc
let outh = outputHandle prc
var stor = newSelector[string]()
defer: stor.close()
stor.registerHandle(int errh, {Read}, "")
stor.registerHandle(int outh, {Read}, "")
var tempout, temperr: File
running = tempout.open(outh)
running = temperr.open(errh)
var running = true
while running:
  let keys = stor.select -1
  for k in keys:
if k.errorCode.int != 0:
  echo k.errorCode.osErrorMsg()
  running = false
  continue
if k.fd == outh:
  echo "stdout: ", tempout.readLine
elif k.fd == errh:
  echo "stderr: ", temperr.readLine
close prc
  else:
echo "on windows"
let prc = startProcess("./a.exe", options = {})
var errstream = errorStream prc
var outstream = outputStream prc
while true:
  var data = errstream.readLine
  if data == "":
break
  else:
echo "stderr: ", data
  data = outstream.readLine
  if data == "":
break
  else:
echo "stdout: ", data

main()


Run

Note that on windows, selectors doesn't work with file, trying to use 
createIoCompletionPort apparently couldn't work because the pipe is busy, 
because of this also we cannot use ReOpenFile to enable flag 
FILE_FLAG_OVERLAPPED. But, we got stream there so we can emulate async with 
peek proc variants (peekStr and peekLine). cmiiw


Re: How to upload large files efficiently and quickly with Jester?

2020-01-21 Thread mashingan
> it seems there is a offset error in the code (files are not identically but 
> shifted by some bytes at certain offsets)

This is quite tricky to find out, TBH. I tried running it on windows and debian 
(in virtual box) and using chromium and firefox (both on windows) and it gave 
the correct files. I hadn't tried with linux box yet though.

> Will the websocket work if I use the nginx as a frontend with ssl?

it's supposed to be working fine, nginx would handle the handshake and the apps 
would only receive the socket connection, I remembered there's some option to 
be set to enable websocket on nginx, but never actually tried it too tho.


Re: How to upload large files efficiently and quickly with Jester?

2020-01-19 Thread mashingan
Uploading file has been tricky, but thankfully nowadays there's websocket to 
send blob. Here's example how to send a file.


import os, jester, asyncdispatch, htmlgen, asyncfile, asyncstreams, streams
import strutils
import ws, ws/jester_extra

settings:
  port = Port 3000

routes:
  get "/":
var html = """

function submit_file() {
  let ws = new WebSocket("ws://localhost:3000/ws-upload");
  let filedom = document.querySelector("#input-field");
  ws.onmessage = function(evnt) {
console.log(evnt.data);
  }
  ws.onopen = function(evnt) {
ws.send(filedom.files[0].name);
ws.send(filedom.files[0].slice());
ws.close();
  }
  return true;
}

"""
for file in walkFiles("*.*"):
  html.add "" & file & ""
html.add ""
html.add ""
html.add ""
html.add ""
resp(html)
  
  get "/ws-upload":
try:
  var wsconn = await newWebSocket(request)
  await wsconn.send("send the filename")
  var fname = await wsconn.receiveStrPacket()
  var f = openAsync(fname, fmWrite)
  while wsconn.readyState == Open:
let (op, seqbyte) = await wsconn.receivePacket()
if op != Binary:
  resp Http400, "invalid sent format"
  wsconn.close()
  return
var cnt = 0
if seqbyte.len < 4096:
  await f.write seqbyte.join
  continue

while cnt < (seqbyte.len-4096):
  let datastr = seqbyte[cnt .. cnt+4095].join
  cnt.inc 4096
  await f.write(datastr)

wsconn.close()
  f.close()
except:
  echo "websocket close: ", getCurrentExceptionMsg()
resp Http200, "file uploaded"


Run


Re: How to upload large files efficiently and quickly with Jester?

2020-01-18 Thread mashingan
It seems the problem is elsewhere, not on how writing it to file, whether 
sync/async file write.

Idk what to tweak on Jester to support larger chunk processing. As for example 
on writeFromStream (not actually solving the problem tho):


routes:
  post "/upload":
var f: AsyncFile
var fstream = newFutureStream[string]("routes.upload")
try:
  f = openAsync("uploaded.file", fmWrite)
except IOError:
  echo getCurrentExceptionMsg()
  resp Http500, "Cannot upload file"
  return
defer: f.close
var datastream = 
newStringStream(request.formData.getOrDefault("file").body)
var asyncwrite = f.writeFromStream(fstream)
while not datastream.atEnd:
  # read each of 1 MB
  let strdata = datastream.readStr(1024 * 1024)
  await fstream.write strdata
fstream.complete
resp Http200, "uploaded"


Run


Re: Using Nim without garbage collection.

2020-01-18 Thread mashingan
spammer? [https://forum.nim-lang.org/t/5791](https://forum.nim-lang.org/t/5791)


Re: How to upload large files efficiently and quickly with Jester?

2020-01-18 Thread mashingan
try to use 
[writeFromStream](https://nim-lang.github.io/Nim/asyncfile.html#writeFromStream%2CAsyncFile%2CFutureStream%5Bstring%5D).


Re: Why does this proc have side effects?

2020-01-16 Thread mashingan
rand proc has side effect.


Re: Naming conventions - need leading underscore

2020-01-16 Thread mashingan
Having _ as initial variable name only acts as visual cue, it's not related to 
readability or anything.

Having clear/distinct/helpful/noisy visual cues doesn't change the fact whether 
the code is well written or not.

What actually helpful is good structure and sane APIs. Whatever the variable 
name it is.


Re: Check if a procedure exists for a given type at compile time

2020-01-12 Thread mashingan
Same case 
[https://forum.nim-lang.org/t/5792#35941](https://forum.nim-lang.org/t/5792#35941)


Re: Is there a default initializer that can be overloaded?

2020-01-11 Thread mashingan
> Error: overloaded 'initElement' leads to ambiguous calls

You tried to overload using generic but actually proc overload usually done 
with argument types. When you defined generic, it's actually creating overload 
proc based on argument type, for example


proc add[T: SomeInteger](a, b: T): T =
   a + b

discard add(4'u32, 5'u32)
discard add(4'i32, 5'i32)


Run

would actually have


proc add(a, b: uint32): uint32 = a + b
proc add(a, b: int32): int32 = a + b


Run

CMIIW


Re: I wrote some nim code that works, but I don't understand how/why it works.

2020-01-11 Thread mashingan
> template/generic instantiation of + from here

This means + is generic and the real operation/error is elsewhere.


Error: type mismatch: got 
 but expected one of:
  iterator items[T](a: seq[T]): T
 first type mismatch at position: 1
 required type for a: seq[T]
.


Run

Means something error happened to make the compiler couldn't expand to items 
iterator.

You need to expand it by yourself to find out.


proc addConstraints*[T, V](constraints: var Constraints[T, V], choice: T, 
consts: seq[V]) =
  for c in consts:
 constraints[choice].incl c


Run

This will lead to interesting error yet it's crucial that, constraints has no 
key of i:1 (of course, it the `choice` arg supplied). If you know the actual 
error, then you just modify your code to


proc addConstraints*[T, V](constraints: var Constraints[T, V], choice: T, 
consts: seq[V]) =
  let hasKey = choice in constraints:
  for c in consts:
 if hasKey:
   constraints[choice].incl c
 else:
   constraints[choice] = @[c].toHashSet()


Run

That way you avoid the KeyError that thrown out.


Re: Is there a default initializer that can be overloaded?

2020-01-11 Thread mashingan
> I have to provide an initElement proc in the generic module in order to 
> compile foo[T] (line #10). That's the reason there's a forward declaration of 
> initElement (line #7).

I tried your code, removed the forward-declaration and fixed your initElement 
definition and it's working fine.


proc initElement[T: TypeInstance]: T =
  result.c = 'E'

discard foo[TypeInstance]()


Run

I tried with `compile` proc and tried to call with `discard foo[int]()` and the 
compiler throw out error with error message supplied to error pragma.

Try it.


Re: Accessing selectors from dispatcher ? why?

2020-01-11 Thread mashingan
[getIoHandler](https://nim-lang.github.io/Nim/asyncdispatch.html#getIoHandler%2CPDispatcher)
 will returning IOCP Handle on Windows or 
[Selector[AsyncData]](https://github.com/nim-lang/Nim/blob/devel/lib/pure/asyncdispatch.nim#L1137-L1138)
 on Unix


Re: Is there a default initializer that can be overloaded?

2020-01-10 Thread mashingan
If I understand you correctly, you wanted the client/user of the module to 
provide their own initElement proc of their type, didn't you?

In that case, you're able to ensure the compiler to check whether the user 
provide their own initElement using 
[compile](https://nim-lang.github.io/Nim/system.html#compiles%2Cuntyped) proc.


proc foo[T]: T =
   when not compiles(initElement[T]()):
{.error: "please provide initElement proc for your type".}
   result = initElement[T]()


Run


Re: Walking trees without recursive iterators

2020-01-06 Thread mashingan
> If Nim has setjump/longjump features (I've just found them in segfaults 
> library!), I could change that pattern to write two coroutines, consumer and 
> producer.

There's [coro](http://nim-lang.github.io/Nim/coro.html) module in case you 
didn't realize it.

> Is there a standard way to resume an iterator in Nim? For instance, if I save 
> a closure iterator in a stack, after having started looping on it, is there a 
> way to resume the iteration?

Perhaps, I misunderstood, but do you means iterator invocation? You can check 
whether the iterator has finished or not with 
[finished](https://nim-lang.github.io/Nim/system.html#finished%2CT) proc and 
just simply call like `myiterator()` would progress your iterator. You don't 
have to put an iterator in for-loop syntax just to iterate it.


Re: "Returning" a proc from a template

2020-01-06 Thread mashingan
> /usercode/in.nim(25, 15) Error: type mismatch: got 

>From this message is quite clear that your template didn't return the untyped 
>as unchecked proc.

>From your template definition, you just defined a proc that only available 
>within that template scope and you didn't return anything. Simply add a line 
>would imply you're returning something


template cmpTaskField*(fieldName: untyped): untyped =
  proc cmpT(task1, task2: Task): int = cmp(task1.fieldName, task2.fieldName)
  cmpT


Run


Re: Safe access operator - how could this be done?

2019-12-30 Thread mashingan
This immediately leave the proc when across something nil


template safe(obj: typed, field: untyped): untyped =
  if obj.isNil:
return
  `obj`.`field`


type
  MyNullObj = ref object
x: int

proc main =
  var nullobj: MyNullObj
  var notnull = MyNullObj(x: 5)
  echo notnull.safe(x)
  echo "reach here"
  echo nullobj.safe(x)

proc main2 =
  var nullobj: MyNullObj
  var notnull = MyNullObj(x: 5)
  echo nullobj.safe(x)
  echo "cannot reach here"
  echo notnull.safe(x)


main2()
main()


Run

For proc that need to return something, have to set `result` in the function 
before hand, but `result` always has its default value so it's also ok


Re: Using a Case Statement inside a template

2019-12-29 Thread mashingan
Very likely the of-branch cannot evaluate iterator and/or template. The `..<` 
not defined as proc, the workaround is


template test(v: typed) =
  case v
  of low(int) .. pred(5):
echo "under 5"
  else:
echo "5 or above"


Run


Re: hello world issues

2019-12-28 Thread mashingan
> Now what if I wanted to create 32-bit-executable?

In your current cmd session, invoke `set 
PATH=d:\your-mingw32-i686-path-bin;%PATH%` , this way the mingw32 32bit will be 
prioritized.


Re: cast ptr ptr to Nim array

2019-12-27 Thread mashingan
> And good comments everywhere.

That's from Ffmpeg header files comment :D , it's preferable to refer the c 
header file directly as the header also written with documentation there.

> and sometimes there are misspelled variable ...

This very likely because of `:%s/_t//g` :P , I'll fix whenever I find them.

> Did you type that up by hand?

Nah, I only edited from source after c2nim to make sure it's working. For 
several examples the binding works fine. But I'll try many more examples to 
make sure it's ok.

> Also, the avfilter is missing there partly

Will add after learning more about Ffmpeg and its APIs. TBH, I'm noob about 
AV-thingy here so tried to make the binding to familiarize myself with the APIs.

> That seems to be the RIGHT answer. It is a pointer to an array of pointers to 
> the elements. Unfortunately, my bindings are still wrong and the result = nil 
> ... Somewhere I still have a mistake in my bindings.

 **tldr; Edit the source after converted using c2nim to use ``importc`` and 
``header`` pragma**

This was the exact case when I converted avcodec.h, avformat.h etc using c2nim. 
At first, I didn't use header pragma to point which header file it should be 
referred and when debugging it, it's always return nil (or when testing with 
isNil is false but crash when dereferencing the pointer).

So I changed to pragma to properly point which header file and it worked ok. 
Even when debugging the struct name appeared too.


Re: Error: 'solve' doesn't have a concrete type, due to unspecified generic parameters.

2019-12-27 Thread mashingan
Information of `T` and `V` already available from parent function so your 
iterator doesn't have to generic. Also, if a function cannot infer from 
argument, the workaround is that you have to be explicit.


proc allExactCover*[T, V](constraints: Constraints[T, V]): iterator (): 
Solution[T] =
  var
solution: Solution[T]
  
  iterator nilIterator: Solution[T] {.closure.} =
yield @[]
  
  iterator solve: Solution[T] {.closure.} =
var c = initHashSet[V]()
yield solution
  
  try:
return solve
  except KeyError:
return nilIterator

proc sdk: iterator (): Solution[Choice] =
  var constraints = initConstraints[Choice, Constraint]()
  
  return allExactCover[Choice, Constraint](constraints) # explicitly tell 
the type


Run


Re: cast ptr ptr to Nim array

2019-12-26 Thread mashingan
This worked in [my example 
here](https://github.com/mashingan/nimffmpeg/blob/master/fplay.nim#L44)


var streams = cast[ptr UncheckedArray[ptr 
AVStream]](pFormatContext[].streams)

Run

I had issues with that too but I fixed my [FFMpeg 
binding](https://github.com/mashingan/nimffmpeg) too.

I even also had some success with [snippet example 
below](https://github.com/mashingan/nimffmpeg/blob/master/ftut.nim#L64)


var stream = pFormatContext[].streams[i]

Run


Re: Distinct for indices, is it good library Api?

2019-12-25 Thread mashingan
> What do you mean?

If I understand correctly, you defined the Node with information of incoming / 
outgoing Edge


type
  Node*[N] = object ## The graph's node type.
  weight*: N ## Associated node data.
  next: array[2, EdgeIndex] ## Next edge in outgoing and incoming edge 
lists.


Run

This way, you only have 1 Edge for each, 1 for incoming and 1 for outgoing. 
Unless your graph specifically only as a one line flow, a node should be able 
to have several nodes incoming and outgoing but you only defined it as an array 
of two Edge member. If it's seq, you can add it later based on new graph 
connection or any info.

Simply changing the definition into seq should somehow solve the limitation of 
current definition. But since it's in development phase, you would recognize it 
the more you develop it, that's why I mentioned "will be unused". CMIIW


Re: Distinct for indices, is it good library Api?

2019-12-25 Thread mashingan
IMO, It's not worthy to make it distinct, moreover, you should use generic 
instead of int for nodes label.

Unrelated to the question, you should keep the Node definition is literally as 
a node, and keep Edge definition is the connection from Node1 and Node2. The 
array of two nodes index for incoming/outgoing will be unused the more you add 
APIs to your graph.


Re: Problem with C interop/X11 bindings

2019-12-23 Thread mashingan
> there is no nil, it reports wrong size.

I remember something when doing ffmpeg c binding. At first I wrote the binding 
without adding the header pragma, and just simply importc pragma only. In the c 
header file, that particular object actually internal struct that isn't 
included in dev headers, and it's there just as to declare the type/struct.

I debugged that and it was returning nil or something that not nil but would 
crash/segfault if I tried to deref it.

After adding the header pragma then it ran smoothly and when debugging, the gdb 
returning the correct struct name.

Idk if it's related or not, but you can try looking that part.


Re: Object Variants and redefinition of labels or reusbility of field names

2019-12-22 Thread mashingan
Another workaround


type
  
  # The 3 notations refer to the same 3-D entity, and some coordinates are 
shared
  CoordinateSystem = enum
csCar, # Cartesian(x,y,z)
csCyl, # Cylindrical  (r,φ,z)
csSph  # Spherical(ρ,θ,φ)
  
  Coordinates = object
cs: CoordinateSystem # cs is the coordinate discriminator
coor1, coor2, coor3: float # keep this part private
  CoorException* = ref object of Exception

proc x(p: Coordinates): float =
if p.cs != csCar:
  raise newException(Defect, "Only available for Cartesian.")
p.coor1

proc `x=`(p: var Coordinates, xval: float) =
if p.cs != csCar:
  raise newException(Defect, "Only available for Cartesian.")
p.coor1 = xval
# do the same with y, and z, should be succint with templates

proc φ*(p: Coordinates): float =
if p.cs == csCar:
  raise newException(Defect, "Cartesian doesn't support φ field.")
elif p.cs == csCyl:
  result = p.coor2
elif p.cs == csSph:
  result = p.coor3
# do the same with other field

var car1 = Coordinates(cs: csCar,
   coor1: 1.0,
   coor2: 2.0,
   coor3: 3.0)

echo car1.x
car1.x = 1.5
echo car1.x

var car2 = Coordinates(cs: csCyl,
   coor1: 1.0,
   coor2: 2.0,
   coor3: 3.0)

echo car2.φ


Run

Read more about it in [manual page 
here](https://nim-lang.github.io/Nim/manual.html#procedures-properties)


Re: Object Variants and redefinition of labels or reusbility of field names

2019-12-22 Thread mashingan
workaround


import strformat

type
  
  # The 3 notations refer to the same 3-D entity, and some coordinates are 
shared
  CoordinateSystem = enum
csCar, # Cartesian(x,y,z)
csCyl, # Cylindrical  (r,φ,z)
csSph  # Spherical(ρ,θ,φ)
  
  Cartesian = object
x, y, z: float
  Cylindrical = object
r, phi, z: float
  Spherical = object
rho, theta, phi: float
  Coordinates = object
case cs: CoordinateSystem: # cs is the coordinate discriminator
  of csCar:
car: Cartesian
  of csCyl:
cy: Cylindrical
  of csSph:
sph: Spherical

proc `$`(point: Coordinates): string =
  case point.cs
  of csCar: result = &"(x: {point.car.x:5.2f}, y: {point.car.y:5.2f}, z: 
{point.car.z:5.2f})"
  of csCyl: result = &"(r: {point.cy.r:5.2f}, φ: {point.cy.phi:5.2f}, z: 
{point.cy.z:5.2f})"
  of csSph: result = &"(ρ: {point.sph.rho:5.2f}, θ: {point.sph.theta:5.2f}, 
φ: {point.sph.phi:5.2f})"


Run


Re: Problem with C interop/X11 bindings

2019-12-22 Thread mashingan
Idk too, but try to wrap the functionality in some proc like main or anything 
and just call that proc.

Another thing, you can always use gdb to check each variable which one has nil.


Re: How to use private variables when you put all types in one module

2019-12-19 Thread mashingan
> And i dont want to mix the implementation code with type declaration code. I 
> need to split as much code as possible.

In different modules or in different files?

If in different modules, as for now, everything exported are visible to other 
modules that import it.

If it's only needed in different file, use [include 
statement](https://nim-lang.github.io/Nim/manual.html#modules-include-statement)


Re: How to use private variables when you put all types in one module

2019-12-19 Thread mashingan
If you need to access the field from other modules, then it's literally not 
private anymore.

If you have specific function that have to work with that private field, then 
implement it in that common module and have that function exported.

If you want to have read only for that specific field, implement the proc for 
it like


proc myFieldName(o: TheObject): FieldType =
   o.myFieldName


Run

Well, basically, there's no literally should have or shouldn't have when 
organizing it, just need some sense/reasonable organization.


Re: how to create a generic type with constraints?

2019-12-18 Thread mashingan
Checking with 
[compiles](https://nim-lang.github.io/Nim/system.html#compiles%2Cuntyped) 
should enough


when compiles(hash(a)): # a is the T object
  doWith(a)
else:
  {.error: "need hash implementation of " & T.type.}


Run

It's checked during compile-time.


Re: What’s your favorite programming language and why?

2019-12-18 Thread mashingan
Same here, love Erlang's philosophy too :D


Re: Force mutable Seq returns

2019-11-19 Thread mashingan
Perhaps you're looking for [var return 
type](https://nim-lang.github.io/Nim/manual.html#procedures-var-return-type) ?


Re: What is the difference between "writeFile" and "newFileStream" and "write"?

2019-11-09 Thread mashingan
AFAIK, `Stream` is usually when you're dealing with bytes; whether opening 
binary files, or reading/writing network bytes stream, or reading/writing bytes 
to file etc.

Especially for writing bytes, just like in the example.


Re: Creating a type that is a non-contiguous subset of char?

2019-10-30 Thread mashingan
since b is declared as WASDLetters , it's inferred so.

But since it's WASDLetters you won't be able to ord(b) and it's detected during 
compile-time checking.


Re: More elegant way to "invert" a table (hash map, dictionary)

2019-10-30 Thread mashingan
Dunno if more elegant or not, but you can try using mapIt


import tables, sequtils

var int2str = {0: "Zero", 1: "One", 2: "Two", 3: "Three"}.toTable
var str2int = toSeq(int2str.pairs).mapIt((it[1], it[0])).toTable


Run


Re: How to write a shared(static in c++) proc in a type ?

2019-10-26 Thread mashingan
proc in Nim is static


Re: Newbie question: downloading multiple files using async httpclient

2019-10-11 Thread mashingan
Yes, it's whether you to wait with asyncCheck or go with future.failed is up to 
application. But the idea is same.


Re: Newbie question: downloading multiple files using async httpclient

2019-10-11 Thread mashingan
the problem that the client cannot be shared to other download


import httpClient, asyncdispatch

proc download(url: string): Future[string] {.async.} =
await newHttpClient().getContent(url)
}

proc downloadAll(urls: seq[string]) {.async.} =
  var asyncresult = newseq[Future[string]](urls.len)
  for i, url in urls:
asyncresult[i] = download url
  await all(asyncresult)

let urls = @[
  "http://127.0.0.1:5000/json;,
  "http://127.0.0.1:5001/json;,
  "http://127.0.0.1:5002/json;,
]
waitFor downloadAll(urls)

Run


Re: httpClient url with the spaces

2019-10-05 Thread mashingan
[encodeQuery](https://nim-lang.org/docs/uri.html#encodeQuery%2CopenArray%5B%5D)

How to get the documentation based on keyword/name?

  1. Open [the 
index](https://nim-lang.org/docs/uri.html#encodeQuery%2CopenArray%5B%5D) page.
  2. Search the page there with `encodeUrl`.
  3. See available procs related to Uri by clicking the found keyword.



Hope it helps.


Re: Newbie experience with the documentation

2019-09-28 Thread mashingan
Trick to find all procedures that return SomeType: `:) SomeType`


Re: Confusion on implicit integer conversion.

2019-09-10 Thread mashingan
_tldr; if the size of integer is important, always opt to explicit conversion_

* * *

you can define your own `+` operator for your case


proc `+`(x: uint16, y: uint32): uint32 = x.uint32 + y


Run

But then the definition then become tedious if you have to define another with


proc `+`(x: uint32, y: uint64): uint64 = x.uint64 + y


Run

again and again. So the `+` is defined as generic. Since generic doesn't know 
which type should it bind to, so it's logical choice to bind to first argument.


Re: Jester question: passing gcsafe variable into routes

2019-08-30 Thread mashingan
Played the idea of pool connections and wrote some example in [gist 
here](https://gist.github.com/mashingan/7532bd89c4e3bde6526a896a3ae611b7).


Re: Need debugging help

2019-08-26 Thread mashingan
Can you try changing [line 
236](https://github.com/pb-cdunn/nim-help/blob/master/raptor_db.nim#L236) with 
`var sr = SequenceRecord()` ?

I'm not sure but maybe what you're doing is scope-escaping memory? That `var 
sr: SequenceRecord` only available in the stack and it got destroyed after you 
copy (or move?) to `result.seqs.add(sr)`

I cannot run it, currently don't have available linux box currently.


Re: asyncnet and reading from multiple socks

2019-08-24 Thread mashingan
> send connect three sockets and read from each of the asynchronously?

like this?


import asyncnet, asyncdispatch, strutils, random

proc genAddr(): string =
   randomize()
   var
   ip0 = rand(1..255)
   ip1 = rand(255)
   ip2 = rand(255)
   ip3 = rand(255)
   (join([$ip0, $ip1, $ip2, $ip3], "."))

proc main() {.async.} =
   var
 sock0 = newAsyncSocket()
 sock1 = newAsyncSocket()
 sock2 = newAsyncSocket()
 res0: string
 res1: string
 res2: string
 host0 = genAddr()
 host1 = genAddr()
 host2 = genAddr()
   
   await sock0.connect(host0, Port 22)
   await sock1.connect(host1, Port 22)
   await sock2.connect(host2, Port 22)
   let
 read0 = sock0.recvLine()
 read1 = sock1.recvLine()
 read2 = sock2.recvLine()
   
   #[
   var
 read0Complete = false
 read1Complete = false
 read2Complete = false
   
   while true:
 if read0Complete and read1Complete and read2Complete:
   break
 
 if read0.finished and not read0.failed and not read0Complete:
   read0Complete = true
   res0 = read read0
 elif read1.finished and not read1.failed and not read1Complete:
   read1Complete = true
   res1 = read read1
 elif read2.finished and not read2.failed and not read2Complete:
   read2Complete = true
   res2 = read read0
   echo res0
   echo res1
   echo res2
   ]#
   
   # easier, if we just need to wait all results
   for line in await all(read0, read1, read2):
 echo line

waitFor main()


Run

> Issue I'm seeming to have is timeout never occurs upon false connections

Try to wrap with connection future 
[withTimeout](https://nim-lang.github.io/Nim/asyncdispatch.html#withTimeout%2CFuture%5BT%5D%2Cint)
 like


let
   conn1 = sock0.connect(host, Port 22).withTimeout(1000)
   conn2 = sock1.connect(host, Port 22).withTimeout(1000)
   conn3 = sock2.connect(host, Port 22).withTimeout(1000)

if not await(conn1) or not await(conn2) or not await(conn3):
   echo "timeout reached in any connection"


Run

_#untested_


Re: Erroneous values returned from Nim’s C foreign function interface.

2019-07-31 Thread mashingan
I'm not sure but after I see in your wutilc


char buffer[INET6_ADDRSTRLEN];

char *get_from(...) {
 \\
 return buffer;
}


Run

I guess it's the problem with global variable; you should change the c api too


void *get_from(struct utmpx *ut, char* outaddr) {
}


Run

and call it in nim


# 
var addrbuf = alloc0(INET6_ADDRSTRLEN)
getfrom(u, addrbuf)
# ...
dealloc(addrbuf)


Run


Re: D templated codeblocks

2019-07-14 Thread mashingan
> (calling again with the same type param does not create a new code block)

This doesn't seem good idea.


Re: dynamic lib works properly when interfacing with python, fails with nim

2019-07-09 Thread mashingan
Try `cdecl` calling convention or others like mentioned in [manual 
page](https://nim-lang.github.io/Nim/manual.html#types-procedural-type)


Re: CORS in Jester

2019-07-09 Thread mashingan
Maybe your client-side hit with pre-flight request.


Re: Simple coroutine like Python generator send()?

2019-06-19 Thread mashingan
Read about iterator in 
[manual](https://nim-lang.github.io/Nim/manual.html#iterators-and-the-for-statement)

[playground](https://play.nim-lang.org/index.html?ix=1MaK)


proc countTo(maxi: int): iterator(x = 1): int =
  result = iterator(x = 1): int =
var i = 0
while i <= maxi:
i.inc x
yield i

var itx3 = countTo 3
echo itx3(2)

if not itx3.finished:
echo itx3()


Run


Re: How to parse the timezone from a date/time string to a `TimeZone` type variable?

2019-06-07 Thread mashingan
something like this


import times, strutils, sugar
let
  dtStr = "2019/06/06 18:17:43 +02:00"
  dt = parse(dtStr, "/MM/dd HH:mm:ss zzz")
  myM10 = newTimezone("M-10",
(x: Time) => ZonedTime(utcOffset: Hours.convert(Seconds, 10), time: x),
(x: Time) => ZonedTime(utcOffset: Hours.convert(Seconds, 10), time: x))
  dtOffset = -1 * dtStr.rsplit(maxsplit=1)[1].split(":", 
maxsplit=1)[0].parseInt
  dtTz = newTimezone("DtTz",
(x: Time) => ZonedTime(utcOffset: Hours.convert(Seconds, dtOffset), 
time: x),
(x: Time) => ZonedTime(utcOffset: Hours.convert(Seconds, dtOffset), 
time: x))
  dtOrig = dt.inZone(dtTz)
  dtMy = dt.inZone(myM10)
echo dt
echo dt.timezone
echo dt.utcOffset
echo ""
echo dtOrig
echo dtOrig.timezone
echo dtOrig.utcOffset
echo ""
echo dtMy
echo dtMy.timezone
echo dtMy.utcOffset


Run

note:

  1. offset should really calculate hours and minutes offset
  2. idk why it should be reverted with -1 for setting the timezone (maybe 
because of time-relativity)
  3. you can write an array that populate with timezone at 1 hour interval at 
compile-time
  4. (or) you can provide some external timezone data and read it at 
compile-time or run-time



IMO, the current times module is more pleasant to work with compared to earlier 
version, kudos for the dev :3


Re: How to parse the timezone from a date/time string to a `TimeZone` type variable?

2019-06-06 Thread mashingan
there's [utc](https://nim-lang.github.io/Nim/times#utc%2CDateTime) proc for 
what you want


import times
let
  dtStr = "2019/06/06 18:17:43 +00:00"
  dt = parse(dtStr, "/MM/dd HH:mm:ss zzz").utc
echo dt


Run


Re: Trouble when splitting in a CLI application

2019-05-29 Thread mashingan
parseopt of course can extract the argument too


import parseopt

let cmdline = "config create \"a configuration\""
var opt = initOptParser(cmdline)
for kind, key, val in opt.getOpt():
  case kind
  of cmdArgument:
echo "argument: ", key
  else:
discard


Run


Re: about Nim compiler parameters

2019-05-28 Thread mashingan
> -d:ssl

This is same with `--define:ssl` , two hyphens is long option while single 
hyphen is short option.

This `--define` option is to define a compile-time variable ala `#DEFINE` in C

for example you define 'goThisWay' when compiling then you can use it in code


when defined(goThisWay):
   # all codes that will be compiled
else:
  # alternative when you want other codes


Run

Another use is explained in this [part of 
manual](https://nim-lang.github.io/Nim/manual.html#implementation-specific-pragmas-compile-time-define-pragmas)


Re: Is there a 'protected' or module-local scope modifier?

2019-05-26 Thread mashingan
elaborate example case please.


Re: Metaprogramming and wrapping C libraries

2019-05-20 Thread mashingan
also you can use 
[quote](https://nim-lang.github.io/Nim/macros.html#quote%2Ctyped%2Cstring) proc 
which easier to use


macro compileFiles(path: static[string], files: untyped): untyped =
  result = newStmtList()
  for f in files:
let file = newLit(path & $f)
result.add quote do:
  {.compile: `file`.}

compileFiles("/base/path/"):
  "a.c"
  "b.c"
  "c.c"


Run


Re: Nim false redefinition error

2019-05-19 Thread mashingan
try remove nimcache folder


Re: Thread and socket functions issue

2019-05-18 Thread mashingan
compile with option `--threads:on`


Re: Conditional compilation in imported module based on constant?

2019-05-10 Thread mashingan
> Can I specify binary-specific defines for the nimble build process?

You can specify which kind of binary built with nimble task. See 
[here](https://github.com/nim-lang/nimble#creating-packages)

You can also make a config file specific to your nim file so the name is 
_yourfile.nim.cfg_ and put the options in it like


-d:it_is_for_algo{1,2}


Run

So whenever `nim c yourfile.nim` is invoked, it automatically add options 
specified in your config file.


Re: New to Nim, Made Something to Feed It

2019-05-07 Thread mashingan
> I’ve used the to(type) macro in other code, but is there a reason to use it 
> over getStr()?

Well, it's convenience, because most of times it's unwieldly to get all the 
fields one by one


Re: New to Nim, Made Something to Feed It

2019-05-07 Thread mashingan
Welcome :)

Additional info, you can use 
[to](https://nim-lang.github.io/Nim/json.html#to.m%2CJsonNode%2Ctypedesc) macro 
to simplify conversion from _JsonNode_ to specified type ;)


Re: Nim vs D

2019-05-04 Thread mashingan
perhaps what you want is 
[quote](https://nim-lang.github.io/Nim/macros.html#quote%2Ctyped%2Cstring) proc?


Re: WideCString -> seq conversion

2019-04-25 Thread mashingan
Have you tried of `runes` in `unicode` module?

It's template that to convert `string` to `seq[Rune]`


Re: Nimongo comparison (i.e. $gt) queries

2019-04-23 Thread mashingan
> `"{$gt:10}".toBson`

This is string, not bson embedded object, what you need is


let query = %{
"temp": {
"$gt": 10
}
}


Run


Re: Not-so-distinct types

2019-04-18 Thread mashingan
If the mapping is fixed, you can use 
[subrange](https://nim-lang.org/docs/manual.html#types-subrange-types) types.

Although the base type is same, you can define like


type
Row1 = range[ 0 .. 71 ] # assuming row has 72 bytes
Row2 = range[ 72 .. 143 ]


Run

Maybe like that?


Re: Not-so-distinct types

2019-04-18 Thread mashingan
Is [distinct](https://nim-lang.org/docs/manual.html#types-distinct-type) not 
what you need?

You can define the needed operations from its base type using `borrow` pragma 
so you don't have to cast/coerce every time you use it

Also, I did what @cdome suggested, defining `converter` s and it works like 
charm. I have several subtype and using converters to convert back and forth 
between the base type and its subtype.


Re: pegs module: how to use captures in enter/leave procs?

2019-04-16 Thread mashingan
Haven't tried the event parser, but if only capturing the needed text I usually 
use `find` proc


var buffer = newseq[string](10) # crash if the seq not enough
if example =~ grammar:
  discard example.find(grammar, buffer)
  echo buffer

# will print
# ["1", "2", "3", "", "", "", "", "", "", ""]


Run


Re: Is allowing non-matching types for assignment overloading in the development timeline?

2019-04-13 Thread mashingan
Perhaps like this


type IntAp = object
  setInts: array[0 .. 2, int]

converter toIntAp(n: int): IntAp =
  let ints = [n, 0, 0]
  IntAp(setInts: ints)

let n: IntAp = 5


Run


Re: Nim vs V language

2019-04-02 Thread mashingan
My (insignificant) 2cent ;)

> V and Nim are very different. One of V's main philosophies is "there must be 
> only one way of doing things". This results in predictable, simple, and 
> maintanable code.

This is fallacy. Bad written code is bad, no matter what syntax is. The only 
thing that make the software maintainable is documentation.

Predictability is something resulted by how clear the program (or data) flow 
from start to end. Not the syntax of anything or what.

Simplicity comes after several (endless) iteration of how we write the 
software. Hoping to write program with simplicity at first shot? Without even 
understanding the nature of problem we want to solve? Well, good luck with that 
:D


Re: How to compile and run a Nim program on the Android?

2019-03-30 Thread mashingan
try more the recent post 
[https://forum.nim-lang.org/t/3575#22318](https://forum.nim-lang.org/t/3575#22318)


Re: How to compile and run a Nim program on the Android?

2019-03-29 Thread mashingan
Your phone must be root-ed to do that.


Re: Please tell me about jester's "tmpl" files.

2019-03-15 Thread mashingan
It's known as source-code filter and you can read the documentation 
[here](https://nim-lang.org/docs/filters.html)

> Can I re-render the page of tmpl without having to re-compile nim.

You can't, cmiiw.


Re: What is the best way to run a nim program as daemon?

2019-03-11 Thread mashingan
handle with 
[setControlCHook](https://nim-lang.org/docs/system.html#setControlCHook%2Cproc%29)
 proc


Re: What is the best way to run a nim program as daemon?

2019-03-11 Thread mashingan
I usually make the executable as service using [this 
reference](https://gist.github.com/bcap/5397674)


Re: Query Filepath for owner and group ID or name

2019-03-01 Thread mashingan
using [fstat](https://nim-lang.org/docs/posix.html#fstat%2Ccint%2CStat) ?


import posix
var f = open "/home/jacobsin/test.txt"
var s: Stat
discard fstat(cint f, s)


Run


Re: Config file location for loadConfig

2019-02-27 Thread mashingan
There's [getAppDir](https://nim-lang.org/docs/os.html#getAppDir%2C) proc


Re: Noob question: proper way to read binary files byte by byte

2019-02-27 Thread mashingan
memfile is basically loading all content to memory, cmiiw


Re: Noob question: proper way to read binary files byte by byte

2019-02-24 Thread mashingan
use [atEnd](https://nim-lang.org/docs/streams.html#atEnd%2CStream) to check 
whether it's ended or not and use 
[getPosition](https://nim-lang.org/docs/streams.html#getPosition%2CStream) for 
its current position.


import os, streams

var fs = newFileStream(paramStr(1), fmRead)

while not fs.atEnd:
  var one_char = fs.readChar()
  echo one_char


Run


Re: std::pair, std::make_pair, std::find, std::distance in Nim?

2019-02-22 Thread mashingan
You can iterate and check manually like


var
  intpair = newseq[(int, int)]()
  texture: int
  lightmap: int

for thepair in intpair:
  if thepair[0] == texture and thepair[1] == lightmap:
doSomething((texture, lightmap))


Run

or you can use define


type
  IntPair = tuple
a: int
b: int

proc `==`(a, b: IntPair): bool =
  a.a == b.a and a.b == b.b

var
  texture: int
  lightmap: int
  intpairs = newseq[IntPair]()
  thepair = (texture, lightmap)
  pos = intpairs.find thepair

if pos != -1: doSomething(thepair)


Run


Re: Convert string to char

2019-02-21 Thread mashingan
You can't generically represent `string` as `char`, but for your specific case, 
you can do it like this:


import options

proc chr(s: string): Option[char] =
  if s == "\\n": some('\n')
  else: none(char)

let nlinerepr = r"\\n".chr
if nlinerepr.isSome:
   echo nlinerepr.some
let otherstr = "hello".chr
if otherstr.isNone:
   echo "no char repr"


Run


Re: Screencast Series Ideas

2019-02-16 Thread mashingan
> I always get tripped up on "damn, this is all classes and objects, how to I 
> do the same thing in Nim?"

You need to change the perspective of the definition from AS to HAS, but `ref 
object of` is kinda AS too, cmiiw. Thanks for link video btw :)

@ryuukoposting , 1st video is nice, waiting for the next videos :D


Re: template does not create methods?

2019-02-16 Thread mashingan
Change the return template from `int` to `untyped` . I usually think `untyped` 
as `unchecked` for easy understanding but let's wait for other to explain 
better ;)


Re: Fuzzy matching on table keys

2019-02-12 Thread mashingan
Add `hash` function and equality operator `==` for custom key.


import tables, hashes

type
  Fn = proc (args: varargs[string]): int
  FnSignature = tuple
name: string
arity: int
argTypes: seq[string]

proc hash(fns: FnSignature): Hash = fns[0].hash
proc `==`(a, b: FnSignature): bool = a[0] == b[0]

var signatures = newTable[FnSignature, Fn]()

signatures.add(("print", 1, @["any"])) do (args: varargs[string]) -> int:
  discard

echo signatures[("print", 1, @["string"])]("whatev")


Run


Re: How to "install" a newly built Nim on a directory?

2019-02-10 Thread mashingan
import std/math


Re: gladloadgl

2019-02-09 Thread mashingan
your `gladLoadGL` definition is `proc gladLoadGL(load: proc): bool` but you 
invoked `gladLoadGL()` without argument


Re: How to implement a "Walrus" operator like in python 3.8 in Nim?

2019-02-09 Thread mashingan
> ... but if you really want, you can use converters.

... but if you can, you should avoid using `int` for `bool`


Re: vecctor items iterator

2019-02-07 Thread mashingan
items iterator is for immutable object, for mutable one, use mitems


Re: "Nim needs better documentation" - share your thoughts

2019-01-12 Thread mashingan
A.

> 1\. Do you think there should be more links to the existing (user-created) 
> resources? If so, which ones?

Yes, but I don't know.

> 2\. What resources are needed? Video tutorials, how-to tutorials for some 
> field X (what is X for you?), cookbook (there is/was one, but it seems it is 
> not updated anymore), etc.

Complete how-to tutorials: web development, machine learning with _Arraymancer_ 
, mobile dev. Those are niche topics currently, the easier and more complete 
the tutorial should make entry barrier lower for people to use/try Nim

> 3\. Have you used Rosetta Code for learning how to do things in Nim? Do you 
> find it useful?

Yes, but quite rarely. Usually when I have no specific thing to do.

> 4\. Have you used code practice sites like Exercism to learn Nim (or some 
> other language)? Do you think they are useful for learning the language? (Or 
> in Nim case: would they be useful if they had more Nim exercises availbable?)

Never used it. Yes, I think it's useful for learning Nim.

B

> 5\. Can you show us the examples of 'good documentation' (GD, later in the 
> text) in other programming languages?

Python documentation, Rust (but it's introduction book, not the their 
documentation, strangely, I found Nim documentation is easier to read than 
Rust's, it's just need some example and elaborate explanation on how to use the 
module/libs)

> 6\. What does the GD consist of? For each module, a general explanation of 
> what it does, code examples of its usage? Long explanations of each 
> function/type/constant? Lots of examples for each function? Links to other 
> modules? Something else?

Yes pretty much like this.

> 7\. What is you major pain point when using Nim documentation? Is it hard to 
> find the module(s) which would be useful to you? Can you understand what a 
> function does based on the description and the example? Are (most of the 
> time) the examples missing or not informative enough?

Nothing major but need time to browse the list and getting familiar with any 
libs available (for the first time), afterward I usually just head to 
"the_index".

Sometimes I understand, mostly not. I understand if I have been working with 
that libs quite often, but when first time using it, need time to digest the 
information. (but it's normally like that right?)

_Asyncdispatch_ and _strscans_ has elaborate explanation, as for 
_asyncdispatch_ unfortunately that's still not enough for me on how to use it 
effectively :/

> 8\. Is there any Nim module which satisfies your criteria for GD? (It is good 
> as it is, doesn't need any improvements)

If we think the GD is like Python's doc, then none. But pretty much the current 
doc is mostly self-explainable for me.

> 9\. Can you show us Nim modules which, in your opinion, have very good 
> documentation? (Only small improvements are needed to make it GD)

[strscans](https://nim-lang.org/docs/strscans.html)

> 10\. Are you willing to help making Nim documentation better? :)

More than willing, just need the documentation, ehem I mean guide :D , to 
contribute to documentation 


Re: Nim and Project Euler

2019-01-12 Thread mashingan
This is my opinion so I have no "hard-data" to backup, I think most (if not 
all) Nim users are people who already have experience with other languages. 
People will gravitate to something that have most lib, most tutorial, most 
documentation, and most easiest for solving their real-life problems (e.g. 
Python which have sheer amount of libs and documentation/tutorial)

This also my opinion, I think another reason why people solving problems in 
Project Euler (other than recreation ofc) is to get familiar with syntaxes. 
Means, few people solving problem in Project Euler using Nim shouldn't 
something that alarming, it's just Nim syntax is so easy that they can pick it 
up easily. (Again, this is my opinion).


Re: Some nim builtin libs not doing enough error checking?

2019-01-11 Thread mashingan
Same here, I prefer checked it first with 
[dirExists](https://nim-lang.org/docs/os.html#dirExists%2Cstring) than 
immediately walk it.


  1   2   3   4   >